How can i get enum to contain a dash (-)?
Asked Answered
V

4

23

I'm generating business objects from this schema using Enterprise Architect.

The schema has the following enumeration specification:

<xs:simpleType name="PackageMedium">
    <xs:restriction base="xs:string">
        <xs:enumeration value="NTP"/>
        <xs:enumeration value="DAT"/>
        <xs:enumeration value="Exabyte"/>
        <xs:enumeration value="CD-ROM"/>
        <xs:enumeration value="DLT"/>
        <xs:enumeration value="D1"/>
        <xs:enumeration value="DVD"/>
        <xs:enumeration value="BD"/>
        <xs:enumeration value="LTO"/>
        <xs:enumeration value="LTO2"/>
        <xs:enumeration value="LTO4"/>
    </xs:restriction>
</xs:simpleType>

Enterprise architect generates the following code but Visual Studio doesn't like the dash(-) in CD-ROM and will not compile.

public enum PackageMedium : int {
    NTP,
    DAT,
    Exabyte,
    CD-ROM,
    DLT,
    D1,
    DVD,
    BD,
    LTO,
    LTO2,
    LTO4
}

What can i do to make this work?


based on @Craig Stuntz answer i was able to find this article which helped me retrieve these special characters from the Enum.

Verulamium answered 13/1, 2012 at 14:44 Comment(2)
Can you alter it to an underscore?Malachy
@Marnix: I would think not. It's an OGC standard, i would think i need to have it like the schema says.Verulamium
D
27

You can't. Full stop. However, there are workarounds. You can, e.g., use DescriptionAttribute:

public enum PackageMedium : int {
    NTP,
    DAT,
    Exabyte,
    [Description("CD-ROM")]
    CDROM,
    DLT,
    D1,
    DVD,
    BD,
    LTO,
    LTO2,
    LTO4
}

This means, unfortunately, that you have more work to do when mapping values. On the other hand, it at lest compiles.

If you don't like that, pick another workaround, e.g., a dictionary:

var dict = Enum.GetValues(typeof(PackageMedium))
               .Cast<PackageMedium>()
               .Select(v => Tuple.Create(v == PackageMedium.CDROM ? "CD-ROM" : v.ToString(), v))
               .ToDictionary(t => t.Item1, t => t.Item2);

var myEnumVal = dict["CD-ROM"];
Doubletalk answered 13/1, 2012 at 14:48 Comment(5)
If i go with a dictionary or list, will that still "be true" to the schema as it is?Verulamium
And could you please post example code of the Dictionary or List version?Verulamium
Actually, i'll just go with description.Verulamium
Well, I added a dictionary example anyway.Doubletalk
Excellent! Thanks, hmmm now i'm torn. Decisions Decision .Verulamium
I
7

Short answer: No.

The reason being is that the - character is used as a token by the lexer for other purposes such as representing the binary and unary minus operator.

Your best bet is to either remove the - or replace it with some other character that is a valid character in identifier names. The only non-letter character you can generally use is _.

You can find more information in the C# Specification.

Irmgardirmina answered 13/1, 2012 at 14:58 Comment(0)
M
2

I know this is late, but this can be usefull.

Another workaround is to use the XmlEnumAttribute :

public enum PackageMedium : int {
NTP,
DAT,
Exabyte,
[XmlEnumAttribute("CD-ROM")]
CDROM,
DLT,
D1,
DVD,
BD,
LTO,
LTO2,
LTO4
}

It is used to validate an xml with an xsd. No additional code needed.

Merat answered 15/4, 2021 at 12:10 Comment(0)
M
1

A C# identifier must start with an underscore, a character in the Unicode class Lu, Ll, Lt, Lm, Lo, or Nl, or an escape for one of those. All other characters must be from Unicode class Lu, Ll, Lt, Lm, Lo, Nl, Mn, Mc, Nd, Pc or Cf, or an escape for one of those.

Hyphen-minus is of category Pd.

If C# did allow it, you still couldn't use it on a public identifier if you needed to be CLS compliant, as it wouldn't fit its rules either.

This is just as well, as how are you meant to distinguish CD-ROM meaning a particular item in the enum from CD-ROM meaning to apply the - operator with CD as the left hand operand and ROM as the right hand operand?

If that list of possibilities is hard-coded, I'd just remove the hyphen-minus and have CDROM as the label. If it's not hard-coded I'd use a dictionary, as it's resiliant in the face of even more cases where something can't be an identifier.

Marquis answered 13/1, 2012 at 15:3 Comment(2)
How would i use a dictionary? If a dictionary would meet the schema all the same, could you please edit your comment to include code of a dictionary version?Verulamium
Craig is way ahead of me on that :)Marquis

© 2022 - 2024 — McMap. All rights reserved.