How to define constants in Visual C# like #define in C? - c#

In C you can define constants like this
#define NUMBER 9
so that wherever NUMBER appears in the program it is replaced with 9. But Visual C# doesn't do this. How is it done?

public const int NUMBER = 9;
You'd need to put it in a class somewhere, and the usage would be ClassName.NUMBER

static class Constants
{
public const int MIN_LENGTH = 5;
public const int MIN_WIDTH = 5;
public const int MIN_HEIGHT = 6;
}
// elsewhere
public CBox()
{
length = Constants.MIN_LENGTH;
width = Constants.MIN_WIDTH;
height = Constants.MIN_HEIGHT;
}

You can't do this in C#. Use a const int instead.

Check How to: Define Constants in C# on MSDN:
In C# the #define preprocessor
directive cannot be used to define
constants in the way that is typically
used in C and C++.

in c language: #define (e.g. #define counter 100)
in assembly language: equ (e.g. counter equ 100)
in c# language: according to msdn refrence:
You use #define to define a symbol. When you use the symbol as the expression that's passed to the #if directive, the expression will evaluate to true, as the following example shows:
# define DEBUG
The #define directive cannot be used to declare constant values as is typically done in C and C++. Constants in C# are best defined as static members of a class or struct. If you have several such constants, consider creating a separate "Constants" class to hold them.

In C#, per MSDN library, we have the "const" keyword that does the work of the "#define" keyword in other languages.
"...when the compiler encounters a constant identifier in C# source code (for example, months), it substitutes the literal value directly into the intermediate language (IL) code that it produces."
( https://msdn.microsoft.com/en-us/library/ms173119.aspx )
Initialize constants at time of declaration since there is no changing them.
public const int cMonths = 12;

What is the "Visual C#"? There is no such thing. Just C#, or .NET C# :)
Also, Python's convention for constants CONSTANT_NAME is not very common in C#. We are usually using CamelCase according to MSDN standards, e.g. public const string ExtractedMagicString = "vs2019";
Source: Defining constants in C#

Related

Cannot define/undefine preprocessor symbols after first token in file

how I can use #define on c#??
I have this code on c++
#define _DSC_CHANNEL_ERRORS_HPP_
#define DSC_ChannelErrors(value) (DSC_E01_##value)
this can be variable, how I can use it?
all code is on code
C# does not support preprocessor symbols like C++.
You have to define them like this:
public const int NUM = 1;
If you want to create a macro your best option is something like this:
public static readonly Func<T> Macro() {};

Precompile variable value

From what I gather in C# documentation, there doesn't appear to be a way to #define variables like in C/C++. Is this correct? I just want to confirm that I'm not overlooking something. Essentially, I want to use a #define variable in /comments/ within my code:
#define _CLASS_ foo123
...
/// Here is documentation for my class _CLASS_
That's a totally fictitious use case, but hopefully that gets the point across.
C# doesn't have such a preprocessor power as in C++. Quote from MSDN:
The #define preprocessing directive: In C++ the #define directive is
commonly used to declare constant values. In C# the #define directive
cannot be used for this purpose. Constants in C# are best defined as
enumerated types (integral values only) or as static members of a
class or struct. If you have several such constants, consider creating
a separate "Constants" class to hold them.

Assign value to C# enum from C++/CLI const

I've searched through the other answers similar to this topic, but haven't found anything completely relevant. I'm trying to assign values to some enumerations in C#, using values that are marked as static const in a C++/CLI file, which are compiled into a DLL and referenced in the C# project. All of that works fine, except that it gives me the "The expression being assigned to 'XXX' must be constant", which I would expect, if the C++/CLI value wasn't a constant. My C++/CLI code is auto-generated from 3rd-party vendor provided files, so my options for changing that side are extremely limited.
Here's some excerpts:
The C++/CLI file:
public ref class SEVERE_LEVEL sealed {
public:
static const System::Int32 VALUE = 200;
private:
SEVERE_LEVEL() {}
};
And the C# file:
public enum LoggerLevel {
SevereLevel = SEVERE_LEVEL.VALUE // This gives the "must be constant" error
}
There are several different log levels, each defined in their own separate class in the C++/CLI file. I want to use the C# enum as a parameter type in some method calls to ensure only valid values are passed in. Any ideas how to make this work or suggestions on alternative designs?
The C++ const keyword doesn't map into anything in .NET.
C++/CLI adds new context-sensitive keywords to match the .NET functionality: initonly and literal.
If you use literal System::Int32 VALUE = 200; then it should work. There's no magic to make the C# compiler define enums using values that aren't marked "literal" in the .NET metadata.

aliasing basic types and constants in C#

We have a C++ code that defines a unified naming convention (majorly for multiplatform reasons).
For example:
#define FOO_UINT32 unsigned long
and
#define FOO_TRUE true
now, we want to port some of this code to C#.
For the first define in the example I figured out that I need:
using FOO_UINT32 = System.UInt32;
The question is? How do I do the second one?
Since true is not a type, you can't utilize a using directive to alias it. You can create a static class with a const member to get a similar result:
public static class PortConstants
{
public const bool FOO_TRUE = true;
}
Then you can say bool x = PortConstants.FOO_TRUE;. I'd recommend just using true, though.
You may also want to drop the using alias for UInt32 as well, since the CLR type won't be changing, and is consistent across platforms for which a CLR implementation is available.
You would need to define a constant, that is the closest you get.
public const bool FOO_TRUE = true;
Also note that the using "trick" to handle the type alias will be for the file it is defined in only.
Now, the bigger question is, are you porting or converting? By porting I mean that you want to keep the ability to try to merge in updates to the original sourcebase into the port.
With a conversion you're basically reimplementing functionality.
If you're doing the latter, you should dispense with these "tricks" altogether and pick a C#/.NET way of doing it instead.
Note that if you use UInt32 in your code, this type will never change to be 16-bit or 64-bit depending on platform, it will always be 32-bit and unsigned. As such, the need for such alias types to handle platform inconsistencies is greatly reduced in .NET and C# so my advice would be to just dispense with that type alias altogether and use UInt32 instead.
The same goes for FOO_TRUE, true will always be a bool type, regardless of platform.
The best thing for forward-going code is to use the idioms of the platform you're programming on.
Well, I advise not doing this at all... you will be safe using System.UInt32 in the C# code in place of FOO_INT32.
With the true option, it is a value so cannot be aliased. You'd need to make a constant, but again, don't unless it's a good constant in the sense of:
public class Constants
{
public const double PI = 3.14; // good use of constants, accuracy of PI could improve in future.
public const bool FOO_TRUE = true; // bad use of constants, or at the very least, bad naming
}
Static class with consts maybe
public static class Constants
{
public const bool FOO_TRUE = true;
}
C# does provide a #define directive, however
The #define directive cannot be used to declare constant values as is
typically done in C and C++. Constants in C# are best defined as
static members of a class or struct. If you have several such
constants, consider creating a separate "Constants" class to hold
them.
You are better off creating a static class and defining them like so:
public const bool FOO_TRUE = true;
I would ask though, why do you want to do this?
It's a bad idea in C++, where at the very least you should use typedef. In C# it doesn't make sense as portability is guaranteed by the underlying platform. Just don't do it.
You can also use enums if you need, i usually prefer them than constants.
[Flags]
enum FOO_UINT32 : uint
{
MyFlag1 = 0x00000002u,
MyFlag2 = 0x80000000u,
FOO_TRUE = 1,
}
public static class MyFunctions
{
public static function MyFunction(FOO_UINT32 value);
}
// In your code
MyFunctions.MyFunction(FOO_UINT32.MyFlag1 | FOO_UINT32.MyFlag2);
MyFunctions.MyFunction(0);
MyFunctions.MyFunction(FOO_UINT32.FOO_TRUE);
MyFunctions.MyFunction((FOO_UINT32)0x123456);
Plus, it don't allows you to pass integer values without a casting, increasing overall readability and reducing risk of errors.
0 is a special case for enums, so it works.

What is the cost of a #define?

To define constants, what is the more common and correct way? What is the cost, in terms of compilation, linking, etc., of defining constants with #define? It is another way less expensive?
The best way to define any const is to write
const int m = 7;
const float pi = 3.1415926f;
const char x = 'F';
Using #define is a bad c++ style. It is impossible to hide #define in namespace scope.
Compare
#define pi 3.1415926
with
namespace myscope {
const float pi = 3.1415926f;
}
Second way is obviously better.
The compiler itself never sees a #define. The preprocessor expands all macros before they're passed to the compiler. One of the side effects, though, is that the values are repeated...and two identical strings are not necessarily the exact same string. If you say
#define SOME_STRING "Just an example"
it's perfectly legal for the compiler to add a copy of the string to the output file each time it sees the string. A good compiler will probably eliminate duplicate literals, but that's extra work it has to do. If you use a const instead, the compiler doesn't have to worry about that as much.
The cost is only to the preprocessor, when #defines are resolved (ignoring the additional debugging cost of dealing with a project full of #defines for constants, of course).
#define macros are processed by the pre-processor, they are not visible to the compiler. And since they are not visible to the compiler as a symbol, it is hard to debug something which involves a macro.
The preferred way of defining constants is using the const keyword along with proper type information.
const unsigned int ArraySize = 100;
Even better is
static const unsigned int ArraySize = 100;
when the constant is used only in a single file.
#define will increase Compilation time but it will faster in execution...
generally in conditional compilation #define is used...
where const is used in general computation of numbers
Choice is depends upon your requirement...
#define is string replacement. So if you make mistakes in the macros, they will show up as errors later on. Mostly incorrect types or incorrect expressions are the common ones.
For conditional compilation, pre-processor macros work best. For other constants which are to be used in computation, const works good.
CPU time isn't really the cost of using #define or macros. The "cost" as a developer is as follows:
If there is an error in your macro, the compiler will flag it where you referenced the macro, not where you defined it.
You will lose type safety and scoping for your macro.
Debugging tools will not know the value of the macro.
These things may not burn CPU cycles, but they can burn developer cycles.
For constants, declaring const variables is preferable, and for little type-independent functions, inline functions and templates are preferable.

Categories