VB.NET stupidity

Consider the following enum definition (which is defined in a C# assembly)

public enum EntityState:int
{
   New,
   Fetched,
   OutOfSync,
   Deleted
}

OK, now, we have an object which has a property called 'State' and this property is of type EntityState. All great, let's set that property State to EntityState.New in VB.NET:

myObject.State = EntityState.New

Does this statement compile or not? I give you a hint: when I press '.' after EntityState, the intellisense of VS.NET does understand it's an enum and gives the 4 values possible.

No! It does not compile! I even have defined Option Strict, but the VB.NET compiler thinks I'm calling Public Sub New() on EntityState even though I have omitted '()' and the compiler comes up with this brilliant knowledge: "Type '...EntityState' has no constructors'. Gee..., really? Perhaps that was the reason I didn't specify '()' so you might already have known it wasn't a method call, it was an enum value specification, dear compiler.

I have to specify:

myObject.State = EntityState.[New]

What a magnificant solution... Instead of fixing the syntax once and for all: always require '()' for a method call, they opt for a horrible workaround: "add [] around the name that confuses the compiler". Apparently even though the compiler knows it's an enum type and the value is a value of that enum type.

23 Comments

  • 3 words.



    Yucky.

    Foul.

    Disgusting.



    I hate the VB.NET syntax with a passion, no matter how much I look at it, I cannot get myself used to the way it is.



    That whole 'brackets around the keywords' thing has been back since the days of Ms Access (not to say those days have passed yet), if you had any columns that were composed of keywords, you placed [] around them -- I remember spending many hours on that.



    Oh well,



    Regards,



    Matthew Cosier

  • **boggle**



    You're complaining that VB.NET acts oddly when you name an enum value after a keyword? Especially when it's a Java, C#, and C++ keyword, too? Maybe it's just me, but the idea of using a keyword in a list of enum values is just so ugly that I can't care what hacks MS put together to make it actually work.

  • Do you use VB Frans???

  • I supply VB.NET templates with LLBLGen Pro, which generate VB.NET code, and I was testing some changes and ran into this :)



    Normally I don't use VB.NET, due to personal preferences.

  • Well I hear you complaining but I don't see you providing a solution. :)



    What would be acceptible in your eyes? I'd think either:

    a) disallowing the use of keywords as properties

    b) providing a compiler warning to the effect of "you've used a keyword to name your field" with a short helpfile description of the keyword and then throw the error you described above.



  • I did provide a solution: force that method calls have to have '()' specified, always. Also, the compiler should be more aware of what it parses. It simply doesn't understand 'EntityState' is an enum. Even the VB.NET editor understands this! (the compile-in-the-background feature didn't bug on this)



    Furthermore, I programmed the enum in C#. Let's say this enum is used in a new .NET language, ABC. THis ABC language has a keyword 'Foo'. Now, I have an enum and that enum has a value 'Foo'. How am I supposed to prevent an error in language ABC? I can't, nor should I have to. I can't possibly know all keywords of all languages using .NET to prevent a nameclash with some keyword. After all, 'New' is not a keyword in C#.



    Every basic compiler design course will learn you that what the VB.NET compiler did is unacceptable. The reason for this is that it KNOWS what 'New' is in the context of EntityState.New. EntityState is an enum and has just 4 values and because it is an enum, it doesn't have a set of methods. However, it ignores this knowledge and of course because of that runs into trouble.



    So both a) and b) are impossible, because I can't know what keywords there are in the languages which can possibly use my C# code.



    This is also not a problem, because every decent compiler would know what 'EntityState' is, and thus how to treat the '.' and the following stringtoken.



    Even if it was a method of a class, I would only run into trouble in VB.NET as VB.NET calls its constructors 'New'. VB.NET's syntaxis is known to a lot of us, but what about other .NET languages not widely known? What if a language defines 'Copy' as a method name for a construct? I then would run into trouble if I have 'Copy' as a method in my class. I can't avoid that, so it's the responsibility of the language USING the code.



    As this is an enum, not a class, the whole subject on 'New' is thus not important, as this isn't an object I want to call 'New' on (when would anyone want to call 'New' on an existing object...) However the compiler thinks it has to, even though this is not an object nor a class. -> bad compiler.

  • Agree completely with Frans. Blaming YOU for using a VB keyword in C# code is simply nonsense.

    VB compiler sucks in this one. It should know what you're coding against through its previous parsing context (i.e. EntityState enum type).

  • I suppose if someone doesn't agree with you, you just delete their comment...



    Nice.

  • Along the same lines... if you call a constructor with no arguments in VS 2003 the VB editor will actually remove the parentheses. Seems like a step backward for me.



    However, if you call a method with no parameters, in VS 2003, the VB editor will add the parentheses if you omit them.



    Another one of these nice keywords is "Shared" (static).

  • All I said was that it's the design of the language. I could argue about all the bad things that I think C# does... but I won't. It's not for me to say that certain things in C# are bad just because I think the way VB.NET is correct. The point is that this so-called issue you bring up has a solution and is consistant in the language. It's not 'broken'. You argue that New != new... in VB.NET... it does. And yes, New is a keyword. Just as in C# new is a keyword. Just as Dim, Error, Stop, etc. are keywords. I have to put use [Stop] around many of my methods and parameters since it's the best word to use for Stop multimedia. I'm aware that I have to do so... the IDE is also pretty good about pointing it out as well. So, again, what you point out is pointless. I'm doing my best to resist bringing up C#'ism that I think are wrong... since I don't want to get into a C# vs VB.NET... but again, it seems that it's OK to trashtalk VB.NET; got forbid anyone post a similar blog entry similar to this one about C#...

  • You don't have to know what keywords are reserved in VB.NET (if you use the IDE)... It points out the mistake immediately. VB.NET is NOT a language that was designed to be used outside of Visual Studio. Based on your comments, I take it that you are not using the IDE... if you were, the editor would POINT THIS ERROR OUT TO YOU!!!!!! Use the tools available to you and you wouldn't have this problem! Stop using notepad.exe... there's the root of your problem. Your complaining because you are using VB.NET in a manner that anyone else using VB.NET would not be.

  • huh?



    I generate VB.NET code, I'm not typing it. Using templates. FOr obvious reasons I can't use the VB.NET editor for template editing, as the code is ported from C# to VB.NET.



    This results thus in compile errors after code generation, because some construct is illegal in VB.NET. I can live with method names which are VB.NET keywords, I can't live with enum VALUES which are seen as methodcalls.



    Every 1st year CS student learning the basics of parsing knows how to solve this. Still, the VB.NET compiler thinks I'm using a class when I state an enum.



    Btw, IMHO, a language which relies on an editor to be used without errors is not that great. And it's also unnecessary, as the language could have been way more consistent with forced '()' after each method call (it's a new language, therefore it should have been in the language), and the compiler could simply be somewhat smarter to understand enums.

  • My point is... it's like arguing about the which of the following is correct.



    VB.NET



    Dim a(9) As Integer



    C#



    int a(10);



    Both give you an array of integers with index elements between 0 to 9.



    There's just some fundamental differences between the languages. You ***MUST*** know that delcaring arrays are different in the two languages if you are going to work between them. This is just as true with what you point out.



    What you are pointing out has nothing to do with compiler problems (even though you keep saying it is). It's purely a syntax issue. And with that, you are pointing out a problem that is completely pointless.



    I'm not defending that VB.NET is correct... I'm just saying that what you saying that the VB.NET compiler is flawed is not accurate. The language is well defined and the issue that you bring up... EVERY VB.NET developer knows how to work with this so-called issue.



    Asking that () be placed on all methods is **NOT** what VB.NET is about. VB.NET is not about pleasing the C# developer... it's about making VB.NET developers productive.



    Again, if you are going to use both languages, you must learn the quirks between the two. Although VB.NET is where I'd prefer to develop, I use C# as well. I can (but won't) point out thinks I don't like about C#; but I don't because C# is for C# developers... not VB.NET developers! Just because I think that C# does something stupid, does not make VB.NET's way right... or vice versa.

  • I believe it is more the case that they designed it that way specifically, to prevent VB programmers from using reserved words like "class" or "string" in their own code. In treating VB programmers like idiots, they end up building in clunky syntax such as the square bracket issue you described.



    As a VB.NET programmer, I'm so used to this issue, it never bothers me anymore, but you're right...it isn't pretty.



    You think that's bad though? Try translating some C# programmer's code to vb.net, when they subscribe to the lazy C# guide to programming:

    String string

    Int int



    ..drives me crazy....the C# language almost encourages sloppy variable naming...



    :-)

  • int is an alias for Int32, just like Integer is, I dont see the problem...

  • Cory, do you know anything about the base class libraries, C#, or IL? You say:

    C#

    int a(10);

    Both give you an array of integers with index elements between 0 to 9.



    Huh? int a(10)? The C# compiler I have won't take that.



    Then you go on with the utterly silly:



    Dim string As String

    Dim someValue As String = String.Format("{0}", 1)



    And then ask which "string" it's going to use? Guess what? There's only ONE possibility (if the code compiled)! The method [mscorlib]System.String::Format is static, not instance. The VB compiler, for some odd reason, perhaps the same reason it lets you import a class, lets you use static methods right off of instance variables.



    Requiring parens after a method call isn't about making C# programmers happy (most of us don't use VB). It's about making the language more consise and clear. Most of the complaints I hear about why VB syntax should be left alone are from VB programmers who haven't used other languages and don't understand why code should be consistent and clear.



    There is simply no reason why VB shouldn't compile Dim x as someEnum = someEnum.New -- regardless of how it treats parens on methods. You cannot call someClass.New() except from a constructor (or you get a BC30282). Enum's don't have any constructors called, so that's not a possibility. After all, someEnum.Shared works just fine.

  • AAAAAAH!!!



    Your missing the point. My appologies for incorrectly using () where I should have use []. (If still wrong, sorry, I don't spend all day in C#.) The point was that in C# you define an array using the number of elements and VB.NET you use the maximum index element. Which is better? It's not important. Each language has it's difference; learn them.



    And, yes, you are correct, the VB.NET code you point out is 'utterly silly'. However, if the host of this site wouldn't CENSOR entries, you would see that I was responding Michael Teper, who stated "int is an alias for Int32, just like Integer is, I dont see the problem...". Michaels statement was in regards to the following code (posted by someone who was a victim of censorship):



    String string;

    Int int;



    My point with this to point out how silly my code looked if VB.NET would allow you to define a variable named string as String and and integer as Integer.



    Paul Vick has stated that he will go into details why VB.NET has the requirement to add [] around reserved keywords and I'm interested in hearing what he has to say. However, back to my original point... it's in the language, it's by design, it's consistant, it works... get over the problem and find a real problem to focus upon.



    Just as you pointed out, I could argue... Why does C# require [] in some places and () in others. People could argue that it's better and whatnot, however, in the end, it's what the language designers decided to do... probably based on the fact that's what C and Java do and C# is targetted to those kind of developers. No matter what the case is, it's the way that it is... adjust accordingly if you plan on using that language.

  • Cory: I've removed your last comment. YOU type your own comments. If you reply like a 3 year old to my blog I feel free to remove your comment, it's my blog after all. I don't want to go as far as not allowing to comment on VB.NET related blogs but I'm not far from it.



    You totally missed the point of the argument. You keep on moaning about that it is in hte language, by design (!) etc. and that C# has problems too. So? From a compiler perspective, the error it gave me which was the start of this blog entry is totally weird and should not happen.



    VB.NET includes some design decisions which will hurt them in the end, like having everything between '()' instead of sometimes [] and sometimes (). If you can't deal with that, that's your problem, but please LEARN to live with critizism on VB.NET. However you can't as it seems, which is a bummer, because it's unnecessary: it's just a language, not a way of living. Criticizing VB.NET does not critize the users, it critizises the language. Don't take it in a different way, but if you do, again: that's your problem, not mine.



    (feel free to start a blog on how crap C# is, and as I said, I'll probably join you. See the point?)

  • "Paul Vick has stated that he will go into details why VB.NET has the requirement to add [] around reserved keywords and I'm interested in hearing what he has to say. However, back to my original point... it's in the language, it's by design, it's consistant, it works... get over the problem and find a real problem to focus upon."

    I understand why it is in the language, because it is a case insensitive language, which implies that you can only distinguish keyword tokens from identifier tokens by different character sequences, not by casing. That's the theoretical why.



    I disagree it is consistent, because it is not: you place [] sometimes around identifiers, in other times you don't.



    Will you believe me if I say that you can do without [] characters in the vast majority of cases the VB.NET compiler demands you for it? The reason for that is that it doesn't to internal error recovery.



    If I say this:

    Public Function Like() As String

    Return CreateSomeString()

    End Function



    it will not compile. 'Like' is a keyword in VB.NET. Do you see it as a keyword in this context? Not at all. The compiler can thus choose to see it as an identifier too. Problem solved. And this will never be interpreted differently: the context is clear.



    About contexts: "Like" is the same keyword but in a string context, and thus it is found 'normal' that the VB.NET compiler doesn't require you to do this: "[Like]".



    Hold that context concept and move towards the issue at hand: EnumType.New. No-one in his right mind will say I'm calling New there. It's an enum. And not defined in VB.NET either. (please cut the crap about not including keywords in enums, I don't know nor can now all keywords VB.NET has nor any other language). I have to state EnumType.[New], because the compiler thinks I'm calling the constructor. Which is the most wrong conclusion that can be drawn, because an enumtype doesn't have a constructor. It can also only draw this conclusion because omitted () after a methodcall are legit. (so you can't see if it is a methodcall, a property or a public field! how consistent). A couple of bad language decisions add up here.



    Because New is in this context just an enum value (the background compiler in the editor does understand this!) the compiler had to decide it IS a value, BECAUSE it is an enum, BEFORE going into backtracking and trying other possibilities.



    Yes, that's ambiguistic parsing, but VB.NET contains ambigu syntaxis. (I gave an example above: property/public field access or method call, can you tell? -> myObject.Foo -> no. Other example: i = foo(bar). Is foo a method, or an array?)



    IF your language has ambiguistic constructs, include a parser who can deal with ambiguistic constructs. In a lot of areas the VB.NET compiler can, however in other areas it can't and I wonder why.



    (yes, C, C++ and C# can all get rid of the ; as well with a clever parser)

  • What's your problem? I removed *one* comment from you because you behaved like a child IN THAT comment.



    I don't recall removing another one from you, if so, it must be a reaction on the removal of that comment.



    Why is it so goddamn hard for you to behave normally like all others have done in this thread? You are the only one who seems to think he's personally offended by a blog about a silly thing in the VB.NET compiler.



    When I remove a whine-post, you are double offended. You keep on repeating that in every post you make, however you keep on posting here. I clearly wonder why.



    If you want to make a point, make the point. I felt personally insulted with your comment, so I removed it. It's my right to do so, I don't have to stick with insults in my comments.



    But you have achieved one thing: Next time I blog about VB.NET it will be a no-comment-possible blog.

  • Ahh come on! Comments are fun. They help us see who it is that complains about certain features. Then we can make our own decisions on the level of intelligence (or whatever you want to call it) of such people.

  • Michael, that's my point. As said in response to your comments, my comment could have been taken completely out of context since conversation that I was referring to was partially sensored, thus only allow you to hear part of the conversation. I don't mind being called an idiot, if it's deserved ;-)



    As I pointed out, I mistakenly used () instead of []. For that I deserved the comment... no problem with that.



    Frans keeps saying my comments are about being personally insulted by him being critical of VB.NET. That is not the case. I originally stated that VB.NET, concerning the brackets around reserved words is consistant throughout the language. Frans still disagrees that it's consistant. So be it. The fact is, it is consistant... the 'Rule'; if you want to use a reserved word within an enum, as a variable name, a method/property name or as a parameter, you must use the brackets around it. It's not as if it's this way for one thing and not another. Therfore, it's consistant. Frans' problem is purley a lack of knowledge in VB.NET and therefore he states that it must be incorrect and "stupid".



    When I tell him to "get over it" and learn the language, he takes it personally and deletes the comment. Fine... no problem with that. But when he starts removing comments where the comments that follow are making reference to; thus completely destroying the whole conversation thread... that's what I have a problem with.



    His argument is weak. It would be like me pointing out that VB.NET defines arrays by maximum element and C# defines them by the number of elements. Does that add to "VB.NET stupidity"?



    By asking to be removed from this thread, it's only from a perspective that I wish to not participate in something that would possibly get deleted (god forbid I hurt poor Frans' feelings) and just add more to the fragmentation that occurs from censorship. Frans', if you are going to make such entries and ask for feedback, then you need to be willing to accept those comments that might hurt your feelings. At no time did I personally attack you, threaten you, nor use any curse words. I only stated that you are whining about something that you shouldn't be whining about.



    My general rule for comments is if it is related to the discussion and does not contain a half a dozen curse words (thus possibly offending any reader coming along), then the comment stays. If I put something out there for people to be able to comment upon, then I have to be an adult and accept the critisism that may occur. It's what blogging is about. If you feel you can't accept the critism, then either keep your mouth shut (or do as you said and not allow comments).



    Frans wants to have control over people critisizing him, however, he doesn't have a problem in belittling others. He refers to people as three year olds or when discussing VB.NET, the dissing the language designers of as "every 1st year CS student learning the basics of parsing knows how to solve this"; so obviously, they must be idiots since they can't seem to get it right.



    So, again, Michael, I completely agree with you. Leave the comments there so that others can make an informed decision. If based on accurate information people want to see me as some sort of idiot, then at least it's something I've done to myself; not something that occured through the tweaking of a thread to make me look one way or another.



    BTW, if anyone is interested, I'm more than happy to allow people to call me an idiot and tell me to get over it at my blog... I don't sensor crap on a whim... if I do sensor someone, an explaination is given (only exception is blog spam).

  • Your last posting here Cory proves my point. I'm not going to defend myself for the gazillionth time on my on blog. In the 15 years I now post messages to usenet newsgroups I learned some various things, among them a rule to not feed the trolls. Your first comment was a troll to get attention. Your last message here is too.



    "Frans wants to have control over people critisizing him, however, he doesn't have a problem in belittling others. He refers to people as three year olds or when discussing VB.NET, the dissing the language designers of as "every 1st year CS student learning the basics of parsing knows how to solve this"; so obviously, they must be idiots since they can't seem to get it right. "... says it all.



    Case closed. No more comments allowed in VB.NET threads. If you have something to comment on this VB.NET topic, you have your own blog, feel free to rip my arguments apart with your own arguments.

Comments have been disabled for this content.