Andrew Wang
Andrew Wang

Reputation: 441

Compile time checking of conditional compilation symbols in C# (see example)?

In C/C++ you can do something like:

#define IN_USE      (1)
#define NOT_IN_USE (-1)

#define USING( system ) ( 1 / (system) == 1 / IN_USE )

And then:

#define MY_SYSTEM  IN_USE

#if USING( MY_SYSTEM )
    <my_system impl>
#endif

This sort of setup means:

Is it possible to do this in C#? Is there another best practices way to achieve the same effect?

I realize in C# you can do conditional compilation by setting them in the project settings and using #if, but I dislike the fact that something doesn't have to be explicitly undefined. This is the reason in the project settings you have the "DEBUG" and "TRACE" checkboxes. If they weren't there, you'd have no idea you could turn them on.

Upvotes: 3

Views: 1108

Answers (3)

James Curran
James Curran

Reputation: 103495

C# doesn't have a preprocessor, but the compiler is smart enough that if you give it a constant as an if() condition, it will emit/not emit code appropriately, giving the same effect.

// in Conditionals.cs
public static class Conditionals
{
     public const bool MY_SYSTEM = true;

}

// In SomeOther.cs
if (Conditionals.MY_SYSTEM)
{
//  <my_system impl>            
}

Upvotes: 1

plinth
plinth

Reputation: 49179

C# doesn't have the c-preprocessor. It does let you have project-wide or file-wide #define's that can be set to either defined or not-defined. You can use this only from within a #if/#else block and your testing is limited to exists/doesn't exist.

So in your case, in your project settings in VisualStudion, under Build, you would have MY_SYSTEM in the Conditional compilation symbols box.

Generally speaking, you want to factor your modules around class definitions rather than around preprocessor chicanery if at all possible.

Upvotes: 0

Jon Skeet
Jon Skeet

Reputation: 1500185

C# doesn't allow preprocessor symbols to be given values, but you can use #define and #ifdef/#endif. Typically preprocessor symbols are actually defined at a project level within the project properties rather than in code.

You may also be interested in ConditionalAttribute which allows calls to methods decorated with it to be omitted if the relevant preprocessor symbol is not present. (The method itself is still built; it just determines whether calls actually take place or not.)

If you want actual constant values, you can use const and static readonly fields instead.

Upvotes: 2

Related Questions