Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why can't I use string interpolation in an attribute?

Tags:

c#

c#-6.0

I'm writing unit tests (MSTest) in C# 6.0 and I noticed something strange in the way the compiler handles string interpolation in attributes.

Why does this work:

[TestCategory(nameof(MyClass) + "-UnitTest")]

When this doesn't?

[TestCategory($"{nameof(MyClass)}-UnitTest")]

Ignoring the fact that this might not be a great way to categorize my tests; I'm curious why the compiler allows one and not the other.

like image 546
Nate Barbettini Avatar asked Aug 05 '15 22:08

Nate Barbettini


People also ask

Can I use string interpolation?

Beginning with C# 10, you can use string interpolation to initialize a constant string. All expressions used for placeholders must be constant strings. In other words, every interpolation expression must be a string, and it must be a compile time constant.

Why do we use string interpolation in C#?

C# string interpolation is used to format and manipulate strings. This feature was introduced in C# 6. Using string interpolation, we can use objects and expressions as a part of the string interpolation operation. C# string interpolation is a method of concatenating, formatting and manipulating strings.

Which strings do interpolate variables?

String interpolation is common in many programming languages which make heavy use of string representations of data, such as Apache Groovy, Julia, Kotlin, Perl, PHP, Python, Ruby, Scala, Swift, Tcl and most Unix shells.

What is string interpolation in Java?

Strings that contain references to variables or expressions are called interpolated strings. When you use interpolated strings, the embedded expressions and variables are evaluated and the result is inserted into the string. The act of inserting data into a string is called string interpolation.


2 Answers

When the compiler encounters an interpolated string it immediately converts it into a call to String.Format so...

[TestCategory($"{nameof(MyClass)}-UnitTest")]

Becomes...

[TestCategory(string.Format("{0}-UnitTest", nameof(MyClass)))]

Attributes require that their arguments be constant expressions but the above expression will not be evaluated until execution time hence the error...

CS0182 An attribute argument must be a constant expression, typeof expression or array creation expression of an attribute parameter type...

You know all the information is available at compile time but the compiler is not smart enough to figure it out.

nameof works a bit differently than interpolated strings because it is evaluated at compile-time so there is no error.

like image 180
Alex Booker Avatar answered Sep 24 '22 03:09

Alex Booker


Interpolated strings are not constant values. The value is determined at runtime, even though in your case all inputs can be calculated at compile time.

like image 38
Jimmy Avatar answered Sep 21 '22 03:09

Jimmy