|
web
newsgroups
|
|||||||||||||||||||||||
|
|||||||||||||||||||||||
Empty string comparisonsI am having a memory blank at the moment. I have been writing in C# for a number of years and now need to do something in VB.NET, so forgive me such a primitive question. In C#, I test whether a string has a value or not by the following syntax: if (thisString.Trim() == "") { // if true something() } else { // if false somethingelse() } Now, in VB.NET an equivalent does not seem to work: If thisString.Trim() = "" Then ' if true something() Else ' if false somethingelse() End If I cannot get past a False return for the VB comparison. What is the best method for testing whether a string is empty or null? Regards, Neville Lang Hi Neville
Don't know whether this is 'best' or not but it certainly works: If testStr Is Nothing or Len(Trim(testStr)) = 0 Then ' 0 length or null string Else ' string is initialised and not empty End if Cheers Martin Neville Lang wrote: Show quoteHide quote > Hi all, > > I am having a memory blank at the moment. I have been writing in C# for a > number of years and now need to do something in VB.NET, so forgive me such a > primitive question. > > In C#, I test whether a string has a value or not by the following syntax: > > if (thisString.Trim() == "") > { > // if true > something() > } > else > { > // if false > somethingelse() > } > > Now, in VB.NET an equivalent does not seem to work: > > If thisString.Trim() = "" Then > ' if true > something() > Else > ' if false > somethingelse() > End If > > I cannot get past a False return for the VB comparison. What is the best > method for testing whether a string is empty or null? > > > Regards, > Neville Lang Pritcham wrote:
> Hi Neville Just in case you're not aware, the Len() and Trim() functions understand > > Don't know whether this is 'best' or not but it certainly works: > > If testStr Is Nothing or Len(Trim(testStr)) = 0 Then > ' 0 length or null string > Else > ' string is initialised and not empty > End if strings that are Nothing and treat them as empty strings (unlike testStr.Length() or testStr.Trim(), which would obviously throw a NullReferenceException), so you can actually shorten this to: \\\ If Len(Trim(testStr)) = 0 Then ' 0 length or null string Else ' string is initialised and not empty End if /// -- (O)enone Neville Lang ha scritto:
> Now, in VB.NET an equivalent does not seem to work: I usually use:> > If thisString.Trim() = "" Then > ' if true > something() > Else > ' if false > somethingelse() > End If Dim s As String = "" If s.Trim = String.Empty Then MsgBox("is empty") Else MsgBox("is not empty") End If but your version also looks fine to me (unless I am missing to see something)... Tommaso Show quoteHide quote > > I cannot get past a False return for the VB comparison. What is the best > method for testing whether a string is empty or null? > > > Regards, > Neville Lang Your problem probably lies elsewhere - the VB code you posted is the exact
equivalent to the C# code. -- Show quoteHide quoteDavid Anton www.tangiblesoftwaresolutions.com Instant C#: VB to C# converter Instant VB: C# to VB converter Instant C++: C#/VB to C++ converter Instant Python: VB to Python converter "Neville Lang" wrote: > Hi all, > > I am having a memory blank at the moment. I have been writing in C# for a > number of years and now need to do something in VB.NET, so forgive me such a > primitive question. > > In C#, I test whether a string has a value or not by the following syntax: > > if (thisString.Trim() == "") > { > // if true > something() > } > else > { > // if false > somethingelse() > } > > Now, in VB.NET an equivalent does not seem to work: > > If thisString.Trim() = "" Then > ' if true > something() > Else > ' if false > somethingelse() > End If > > I cannot get past a False return for the VB comparison. What is the best > method for testing whether a string is empty or null? > > > Regards, > Neville Lang > > > David,
To be fair on this question, there were some extra things that I did not post in my example that would probably have affected the outcome. So, you may be right in suspecting it might have been elsewhere. Here is the complete picture: Dim someError(259) As Byte Dim thisString As String Dim ret As Integer .... .... ' This function call is one located in a C++ DLL ' The someError argument had Marshaling setup as follows ' <MarshalAs(UnmanagedType.LPArray, SizeConst:=260)> ByVal someError As Byte() ret = externalFunction(a, b, c, someError) thisString = Encoding.ASCII.GetString((someError) ' Now the string comparison. It was found that the ' string's return value was "" but its length was 260, and so all ' combinations of string comparison yielded a False in VB and ' that is why I asked my question. It is from my Compact Framework experience in C# that I got into the habit of setting up Byte arrays for returning error strings from external functions in C++ DLLs, due to P/Invoke Marshaling restrictions in the Compact Framework. And that is what I have continued here too. After reading the various responses here, I feel I am now a bit more knowledgeable on string comparisons. Regards, Neville Lang Show quoteHide quote "David Anton" <DavidAn***@discussions.microsoft.com> wrote in message news:59A9EAC7-EE03-42AF-8D43-EE26682AC303@microsoft.com... > Your problem probably lies elsewhere - the VB code you posted is the exact > equivalent to the C# code. > -- > David Anton > www.tangiblesoftwaresolutions.com > Instant C#: VB to C# converter > Instant VB: C# to VB converter > Instant C++: C#/VB to C++ converter > Instant Python: VB to Python converter > > > "Neville Lang" wrote: > >> Hi all, >> >> I am having a memory blank at the moment. I have been writing in C# for a >> number of years and now need to do something in VB.NET, so forgive me >> such a >> primitive question. >> >> In C#, I test whether a string has a value or not by the following >> syntax: >> >> if (thisString.Trim() == "") >> { >> // if true >> something() >> } >> else >> { >> // if false >> somethingelse() >> } >> >> Now, in VB.NET an equivalent does not seem to work: >> >> If thisString.Trim() = "" Then >> ' if true >> something() >> Else >> ' if false >> somethingelse() >> End If >> >> I cannot get past a False return for the VB comparison. What is the best >> method for testing whether a string is empty or null? >> >> >> Regards, >> Neville Lang >> >> >> The code you have should work just fine. There are other ways to do it as
well though: 1. Use the VB.NET "feature" that null and empty string are considered equal when using the = operator, i.e the following statement: If thisString = "" Then returns true if thisString is either empty *or* null (beware, this does not work in C#) 2. Use the new String.IsNullOrEmpty method (requires .NET 2.0) /claes Show quoteHide quote "Neville Lang" <neville@MAPS_ONnjlsoftware.com> wrote in message news:ucODy9$9GHA.3348@TK2MSFTNGP03.phx.gbl... > Hi all, > > I am having a memory blank at the moment. I have been writing in C# for a > number of years and now need to do something in VB.NET, so forgive me such > a primitive question. > > In C#, I test whether a string has a value or not by the following syntax: > > if (thisString.Trim() == "") > { > // if true > something() > } > else > { > // if false > somethingelse() > } > > Now, in VB.NET an equivalent does not seem to work: > > If thisString.Trim() = "" Then > ' if true > something() > Else > ' if false > somethingelse() > End If > > I cannot get past a False return for the VB comparison. What is the best > method for testing whether a string is empty or null? > > > Regards, > Neville Lang > > Regarding your first point, VB is even stranger than that:
A string set to Nothng (or uninitialized) is regarded as equal to an empty string, but an empty string is *not* regarded as equal to Nothing. C# is consistent in this respect: a null string is a null string and an empty string is an empty string. -- Show quoteHide quoteDavid Anton www.tangiblesoftwaresolutions.com Instant C#: VB to C# converter Instant VB: C# to VB converter Instant C++: C#/VB to C++ converter Instant Python: VB to Python converter "Claes Bergefall" wrote: > The code you have should work just fine. There are other ways to do it as > well though: > > 1. Use the VB.NET "feature" that null and empty string are considered equal > when using the = operator, i.e the following statement: > If thisString = "" Then > returns true if thisString is either empty *or* null (beware, this does not > work in C#) > 2. Use the new String.IsNullOrEmpty method (requires .NET 2.0) > > /claes > > "Neville Lang" <neville@MAPS_ONnjlsoftware.com> wrote in message > news:ucODy9$9GHA.3348@TK2MSFTNGP03.phx.gbl... > > Hi all, > > > > I am having a memory blank at the moment. I have been writing in C# for a > > number of years and now need to do something in VB.NET, so forgive me such > > a primitive question. > > > > In C#, I test whether a string has a value or not by the following syntax: > > > > if (thisString.Trim() == "") > > { > > // if true > > something() > > } > > else > > { > > // if false > > somethingelse() > > } > > > > Now, in VB.NET an equivalent does not seem to work: > > > > If thisString.Trim() = "" Then > > ' if true > > something() > > Else > > ' if false > > somethingelse() > > End If > > > > I cannot get past a False return for the VB comparison. What is the best > > method for testing whether a string is empty or null? > > > > > > Regards, > > Neville Lang > > > > > > > Actually it does (at least in 2.0). All of the following evaluate to True:
Dim s1 As String = "" Dim s2 As String = Nothing Dim b1 As Boolean = (s1 = Nothing) Dim b2 As Boolean = (s2 = Nothing) Dim b3 As Boolean = (s1 = "") Dim b4 As Boolean = (s2 = "") You have to use String.Equals to distinguish between Nothing and an empty string. Personally I find the VB.NET behaviour annoying and would prefer that it worked the same as in C# /claes Show quoteHide quote "David Anton" <DavidAn***@discussions.microsoft.com> wrote in message news:63186DF2-8DE7-4EA4-9927-D6A755AD4596@microsoft.com... > Regarding your first point, VB is even stranger than that: > A string set to Nothng (or uninitialized) is regarded as equal to an empty > string, but an empty string is *not* regarded as equal to Nothing. C# is > consistent in this respect: a null string is a null string and an empty > string is an empty string. > -- > David Anton > www.tangiblesoftwaresolutions.com > Instant C#: VB to C# converter > Instant VB: C# to VB converter > Instant C++: C#/VB to C++ converter > Instant Python: VB to Python converter > > > "Claes Bergefall" wrote: > >> The code you have should work just fine. There are other ways to do it as >> well though: >> >> 1. Use the VB.NET "feature" that null and empty string are considered >> equal >> when using the = operator, i.e the following statement: >> If thisString = "" Then >> returns true if thisString is either empty *or* null (beware, this does >> not >> work in C#) >> 2. Use the new String.IsNullOrEmpty method (requires .NET 2.0) >> >> /claes >> >> "Neville Lang" <neville@MAPS_ONnjlsoftware.com> wrote in message >> news:ucODy9$9GHA.3348@TK2MSFTNGP03.phx.gbl... >> > Hi all, >> > >> > I am having a memory blank at the moment. I have been writing in C# for >> > a >> > number of years and now need to do something in VB.NET, so forgive me >> > such >> > a primitive question. >> > >> > In C#, I test whether a string has a value or not by the following >> > syntax: >> > >> > if (thisString.Trim() == "") >> > { >> > // if true >> > something() >> > } >> > else >> > { >> > // if false >> > somethingelse() >> > } >> > >> > Now, in VB.NET an equivalent does not seem to work: >> > >> > If thisString.Trim() = "" Then >> > ' if true >> > something() >> > Else >> > ' if false >> > somethingelse() >> > End If >> > >> > I cannot get past a False return for the VB comparison. What is the >> > best >> > method for testing whether a string is empty or null? >> > >> > >> > Regards, >> > Neville Lang >> > >> > >> >> >> Claes,
> You have to use String.Equals to distinguish between Nothing and an empty I would recommend using "Is" to distinguish between Nothing and an empty > string. Close! ;-) string. > Dim b5 As Boolean = (s1 Is Nothing) One might consider these two, however they won't always return true:> Dim b6 As Boolean = (s2 Is Nothing) > Dim b7 As Boolean = (s1 Is "") Depending on how s1 & s2 got to be an empty string will change what the last > Dim b8 As Boolean = (s2 Is "") two return. For example: s2 = " ".Trim() Will cause (s2 Is "") to fail, as " ".Trim() returns a new string, where as "" returns an interned string... Remember that = does value equality ("" & Nothing) are considered to have the same value. Where as Is does reference equality ("", " ".Trim() & Nothing) are distinct object references. > Personally I find the VB.NET behavior annoying and would prefer that it Most of the time I agree, there are times though where I prefer the C# > worked the same as in C# behavior. -- Show quoteHide quoteHope this helps Jay B. Harlow ..NET Application Architect, Enthusiast, & Evangelist T.S. Bradley - http://www.tsbradley.net "Claes Bergefall" <louplou@nospam.nospam> wrote in message news:%23f6zIUQ%23GHA.3644@TK2MSFTNGP02.phx.gbl... > Actually it does (at least in 2.0). All of the following evaluate to True: > > Dim s1 As String = "" > Dim s2 As String = Nothing > Dim b1 As Boolean = (s1 = Nothing) > Dim b2 As Boolean = (s2 = Nothing) > Dim b3 As Boolean = (s1 = "") > Dim b4 As Boolean = (s2 = "") > > You have to use String.Equals to distinguish between Nothing and an empty > string. Personally I find the VB.NET behaviour annoying and would prefer > that it worked the same as in C# > > /claes > > "David Anton" <DavidAn***@discussions.microsoft.com> wrote in message > news:63186DF2-8DE7-4EA4-9927-D6A755AD4596@microsoft.com... >> Regarding your first point, VB is even stranger than that: >> A string set to Nothng (or uninitialized) is regarded as equal to an >> empty >> string, but an empty string is *not* regarded as equal to Nothing. C# is >> consistent in this respect: a null string is a null string and an empty >> string is an empty string. >> -- >> David Anton >> www.tangiblesoftwaresolutions.com >> Instant C#: VB to C# converter >> Instant VB: C# to VB converter >> Instant C++: C#/VB to C++ converter >> Instant Python: VB to Python converter >> >> >> "Claes Bergefall" wrote: >> >>> The code you have should work just fine. There are other ways to do it >>> as >>> well though: >>> >>> 1. Use the VB.NET "feature" that null and empty string are considered >>> equal >>> when using the = operator, i.e the following statement: >>> If thisString = "" Then >>> returns true if thisString is either empty *or* null (beware, this does >>> not >>> work in C#) >>> 2. Use the new String.IsNullOrEmpty method (requires .NET 2.0) >>> >>> /claes >>> >>> "Neville Lang" <neville@MAPS_ONnjlsoftware.com> wrote in message >>> news:ucODy9$9GHA.3348@TK2MSFTNGP03.phx.gbl... >>> > Hi all, >>> > >>> > I am having a memory blank at the moment. I have been writing in C# >>> > for a >>> > number of years and now need to do something in VB.NET, so forgive me >>> > such >>> > a primitive question. >>> > >>> > In C#, I test whether a string has a value or not by the following >>> > syntax: >>> > >>> > if (thisString.Trim() == "") >>> > { >>> > // if true >>> > something() >>> > } >>> > else >>> > { >>> > // if false >>> > somethingelse() >>> > } >>> > >>> > Now, in VB.NET an equivalent does not seem to work: >>> > >>> > If thisString.Trim() = "" Then >>> > ' if true >>> > something() >>> > Else >>> > ' if false >>> > somethingelse() >>> > End If >>> > >>> > I cannot get past a False return for the VB comparison. What is the >>> > best >>> > method for testing whether a string is empty or null? >>> > >>> > >>> > Regards, >>> > Neville Lang >>> > >>> > >>> >>> >>> > > >> Personally I find the VB.NET behavior annoying and would prefer that it Huh? (cringle nose).>> worked the same as in C# > Most of the time I agree, there are times though where I prefer the C# > behavior. That didn't come out right. :-) I meant most of the item I agree; Most of the time I prefer the C# behavior. However there are times I like the VB behavior... -- Show quoteHide quoteHope this helps Jay B. Harlow ..NET Application Architect, Enthusiast, & Evangelist T.S. Bradley - http://www.tsbradley.net "Jay B. Harlow" <Jay_Harlow_***@tsbradley.net> wrote in message news:27A229FC-862A-47A5-8527-A2FDAD88773B@microsoft.com... > Claes, >> You have to use String.Equals to distinguish between Nothing and an empty >> string. > Close! ;-) > > I would recommend using "Is" to distinguish between Nothing and an empty > string. > >> Dim b5 As Boolean = (s1 Is Nothing) >> Dim b6 As Boolean = (s2 Is Nothing) > > One might consider these two, however they won't always return true: > >> Dim b7 As Boolean = (s1 Is "") >> Dim b8 As Boolean = (s2 Is "") > > Depending on how s1 & s2 got to be an empty string will change what the > last two return. > > For example: > > s2 = " ".Trim() > > Will cause (s2 Is "") to fail, as " ".Trim() returns a new string, > where as "" returns an interned string... > > Remember that = does value equality ("" & Nothing) are considered to have > the same value. > > Where as Is does reference equality ("", " ".Trim() & Nothing) are > distinct object references. > >> Personally I find the VB.NET behavior annoying and would prefer that it >> worked the same as in C# > Most of the time I agree, there are times though where I prefer the C# > behavior. > > -- > Hope this helps > Jay B. Harlow > .NET Application Architect, Enthusiast, & Evangelist > T.S. Bradley - http://www.tsbradley.net > > > "Claes Bergefall" <louplou@nospam.nospam> wrote in message > news:%23f6zIUQ%23GHA.3644@TK2MSFTNGP02.phx.gbl... >> Actually it does (at least in 2.0). All of the following evaluate to >> True: >> >> Dim s1 As String = "" >> Dim s2 As String = Nothing >> Dim b1 As Boolean = (s1 = Nothing) >> Dim b2 As Boolean = (s2 = Nothing) >> Dim b3 As Boolean = (s1 = "") >> Dim b4 As Boolean = (s2 = "") >> >> You have to use String.Equals to distinguish between Nothing and an empty >> string. Personally I find the VB.NET behaviour annoying and would prefer >> that it worked the same as in C# >> >> /claes >> >> "David Anton" <DavidAn***@discussions.microsoft.com> wrote in message >> news:63186DF2-8DE7-4EA4-9927-D6A755AD4596@microsoft.com... >>> Regarding your first point, VB is even stranger than that: >>> A string set to Nothng (or uninitialized) is regarded as equal to an >>> empty >>> string, but an empty string is *not* regarded as equal to Nothing. C# >>> is >>> consistent in this respect: a null string is a null string and an empty >>> string is an empty string. >>> -- >>> David Anton >>> www.tangiblesoftwaresolutions.com >>> Instant C#: VB to C# converter >>> Instant VB: C# to VB converter >>> Instant C++: C#/VB to C++ converter >>> Instant Python: VB to Python converter >>> >>> >>> "Claes Bergefall" wrote: >>> >>>> The code you have should work just fine. There are other ways to do it >>>> as >>>> well though: >>>> >>>> 1. Use the VB.NET "feature" that null and empty string are considered >>>> equal >>>> when using the = operator, i.e the following statement: >>>> If thisString = "" Then >>>> returns true if thisString is either empty *or* null (beware, this does >>>> not >>>> work in C#) >>>> 2. Use the new String.IsNullOrEmpty method (requires .NET 2.0) >>>> >>>> /claes >>>> >>>> "Neville Lang" <neville@MAPS_ONnjlsoftware.com> wrote in message >>>> news:ucODy9$9GHA.3348@TK2MSFTNGP03.phx.gbl... >>>> > Hi all, >>>> > >>>> > I am having a memory blank at the moment. I have been writing in C# >>>> > for a >>>> > number of years and now need to do something in VB.NET, so forgive me >>>> > such >>>> > a primitive question. >>>> > >>>> > In C#, I test whether a string has a value or not by the following >>>> > syntax: >>>> > >>>> > if (thisString.Trim() == "") >>>> > { >>>> > // if true >>>> > something() >>>> > } >>>> > else >>>> > { >>>> > // if false >>>> > somethingelse() >>>> > } >>>> > >>>> > Now, in VB.NET an equivalent does not seem to work: >>>> > >>>> > If thisString.Trim() = "" Then >>>> > ' if true >>>> > something() >>>> > Else >>>> > ' if false >>>> > somethingelse() >>>> > End If >>>> > >>>> > I cannot get past a False return for the VB comparison. What is the >>>> > best >>>> > method for testing whether a string is empty or null? >>>> > >>>> > >>>> > Regards, >>>> > Neville Lang >>>> > >>>> > >>>> >>>> >>>> >> >> > Yes, but try:
Dim s1 As String = "" Dim b1 As Boolean = (s1 Is Nothing) b1 evaluates to false. Isn't VB fun?! -- Show quoteHide quoteDavid Anton www.tangiblesoftwaresolutions.com Instant C#: VB to C# converter Instant VB: C# to VB converter Instant C++: C#/VB to C++ converter Instant Python: VB to Python converter "Claes Bergefall" wrote: > Actually it does (at least in 2.0). All of the following evaluate to True: > > Dim s1 As String = "" > Dim s2 As String = Nothing > Dim b1 As Boolean = (s1 = Nothing) > Dim b2 As Boolean = (s2 = Nothing) > Dim b3 As Boolean = (s1 = "") > Dim b4 As Boolean = (s2 = "") > > You have to use String.Equals to distinguish between Nothing and an empty > string. Personally I find the VB.NET behaviour annoying and would prefer > that it worked the same as in C# > > /claes > > "David Anton" <DavidAn***@discussions.microsoft.com> wrote in message > news:63186DF2-8DE7-4EA4-9927-D6A755AD4596@microsoft.com... > > Regarding your first point, VB is even stranger than that: > > A string set to Nothng (or uninitialized) is regarded as equal to an empty > > string, but an empty string is *not* regarded as equal to Nothing. C# is > > consistent in this respect: a null string is a null string and an empty > > string is an empty string. > > -- > > David Anton > > www.tangiblesoftwaresolutions.com > > Instant C#: VB to C# converter > > Instant VB: C# to VB converter > > Instant C++: C#/VB to C++ converter > > Instant Python: VB to Python converter > > > > > > "Claes Bergefall" wrote: > > > >> The code you have should work just fine. There are other ways to do it as > >> well though: > >> > >> 1. Use the VB.NET "feature" that null and empty string are considered > >> equal > >> when using the = operator, i.e the following statement: > >> If thisString = "" Then > >> returns true if thisString is either empty *or* null (beware, this does > >> not > >> work in C#) > >> 2. Use the new String.IsNullOrEmpty method (requires .NET 2.0) > >> > >> /claes > >> > >> "Neville Lang" <neville@MAPS_ONnjlsoftware.com> wrote in message > >> news:ucODy9$9GHA.3348@TK2MSFTNGP03.phx.gbl... > >> > Hi all, > >> > > >> > I am having a memory blank at the moment. I have been writing in C# for > >> > a > >> > number of years and now need to do something in VB.NET, so forgive me > >> > such > >> > a primitive question. > >> > > >> > In C#, I test whether a string has a value or not by the following > >> > syntax: > >> > > >> > if (thisString.Trim() == "") > >> > { > >> > // if true > >> > something() > >> > } > >> > else > >> > { > >> > // if false > >> > somethingelse() > >> > } > >> > > >> > Now, in VB.NET an equivalent does not seem to work: > >> > > >> > If thisString.Trim() = "" Then > >> > ' if true > >> > something() > >> > Else > >> > ' if false > >> > somethingelse() > >> > End If > >> > > >> > I cannot get past a False return for the VB comparison. What is the > >> > best > >> > method for testing whether a string is empty or null? > >> > > >> > > >> > Regards, > >> > Neville Lang > >> > > >> > > >> > >> > >> > > > Ahh, yes. The Is operator behaves different from the = operator.
VB is hilarious :-) /claes Show quoteHide quote "David Anton" <DavidAn***@discussions.microsoft.com> wrote in message news:C21FAC70-9BA6-4FE4-A541-6C359ADD3EB4@microsoft.com... > Yes, but try: > Dim s1 As String = "" > Dim b1 As Boolean = (s1 Is Nothing) > > b1 evaluates to false. Isn't VB fun?! > -- > David Anton > www.tangiblesoftwaresolutions.com > Instant C#: VB to C# converter > Instant VB: C# to VB converter > Instant C++: C#/VB to C++ converter > Instant Python: VB to Python converter > > > "Claes Bergefall" wrote: > >> Actually it does (at least in 2.0). All of the following evaluate to >> True: >> >> Dim s1 As String = "" >> Dim s2 As String = Nothing >> Dim b1 As Boolean = (s1 = Nothing) >> Dim b2 As Boolean = (s2 = Nothing) >> Dim b3 As Boolean = (s1 = "") >> Dim b4 As Boolean = (s2 = "") >> >> You have to use String.Equals to distinguish between Nothing and an empty >> string. Personally I find the VB.NET behaviour annoying and would prefer >> that it worked the same as in C# >> >> /claes >> >> "David Anton" <DavidAn***@discussions.microsoft.com> wrote in message >> news:63186DF2-8DE7-4EA4-9927-D6A755AD4596@microsoft.com... >> > Regarding your first point, VB is even stranger than that: >> > A string set to Nothng (or uninitialized) is regarded as equal to an >> > empty >> > string, but an empty string is *not* regarded as equal to Nothing. C# >> > is >> > consistent in this respect: a null string is a null string and an empty >> > string is an empty string. >> > -- >> > David Anton >> > www.tangiblesoftwaresolutions.com >> > Instant C#: VB to C# converter >> > Instant VB: C# to VB converter >> > Instant C++: C#/VB to C++ converter >> > Instant Python: VB to Python converter >> > >> > >> > "Claes Bergefall" wrote: >> > >> >> The code you have should work just fine. There are other ways to do it >> >> as >> >> well though: >> >> >> >> 1. Use the VB.NET "feature" that null and empty string are considered >> >> equal >> >> when using the = operator, i.e the following statement: >> >> If thisString = "" Then >> >> returns true if thisString is either empty *or* null (beware, this >> >> does >> >> not >> >> work in C#) >> >> 2. Use the new String.IsNullOrEmpty method (requires .NET 2.0) >> >> >> >> /claes >> >> >> >> "Neville Lang" <neville@MAPS_ONnjlsoftware.com> wrote in message >> >> news:ucODy9$9GHA.3348@TK2MSFTNGP03.phx.gbl... >> >> > Hi all, >> >> > >> >> > I am having a memory blank at the moment. I have been writing in C# >> >> > for >> >> > a >> >> > number of years and now need to do something in VB.NET, so forgive >> >> > me >> >> > such >> >> > a primitive question. >> >> > >> >> > In C#, I test whether a string has a value or not by the following >> >> > syntax: >> >> > >> >> > if (thisString.Trim() == "") >> >> > { >> >> > // if true >> >> > something() >> >> > } >> >> > else >> >> > { >> >> > // if false >> >> > somethingelse() >> >> > } >> >> > >> >> > Now, in VB.NET an equivalent does not seem to work: >> >> > >> >> > If thisString.Trim() = "" Then >> >> > ' if true >> >> > something() >> >> > Else >> >> > ' if false >> >> > somethingelse() >> >> > End If >> >> > >> >> > I cannot get past a False return for the VB comparison. What is the >> >> > best >> >> > method for testing whether a string is empty or null? >> >> > >> >> > >> >> > Regards, >> >> > Neville Lang >> >> > >> >> > >> >> >> >> >> >> >> >> >> > Ahh, yes. The Is operator behaves different from the = operator. JavaScript has the Equality "==" (two equals) and the Identity "===" (three > VB is hilarious :-) How so? equals) operators. VB also has an Equality "=" (one equals) and an Identity "Is" operators. Identity & Equality although very closely related are not synonymous. What I find interesting is that JavaScript has a Non Identity operator "!==" and VB 2005 introduced a Not Identity operator IsNot, but VB decided to patent theirs... I find it unfortunate & slightly confusing that C# blurs Equality with Identity with a single operator "=" & "!="; Granted you can still use Object.ReferenceEquals in C# for Identity... -- Show quoteHide quoteHope this helps Jay B. Harlow ..NET Application Architect, Enthusiast, & Evangelist T.S. Bradley - http://www.tsbradley.net "Claes Bergefall" <louplou@nospam.nospam> wrote in message news:e1XVM%23c%23GHA.924@TK2MSFTNGP03.phx.gbl... > Ahh, yes. The Is operator behaves different from the = operator. > VB is hilarious :-) > > /claes > > "David Anton" <DavidAn***@discussions.microsoft.com> wrote in message > news:C21FAC70-9BA6-4FE4-A541-6C359ADD3EB4@microsoft.com... >> Yes, but try: >> Dim s1 As String = "" >> Dim b1 As Boolean = (s1 Is Nothing) >> >> b1 evaluates to false. Isn't VB fun?! >> -- >> David Anton >> www.tangiblesoftwaresolutions.com >> Instant C#: VB to C# converter >> Instant VB: C# to VB converter >> Instant C++: C#/VB to C++ converter >> Instant Python: VB to Python converter >> >> >> "Claes Bergefall" wrote: >> >>> Actually it does (at least in 2.0). All of the following evaluate to >>> True: >>> >>> Dim s1 As String = "" >>> Dim s2 As String = Nothing >>> Dim b1 As Boolean = (s1 = Nothing) >>> Dim b2 As Boolean = (s2 = Nothing) >>> Dim b3 As Boolean = (s1 = "") >>> Dim b4 As Boolean = (s2 = "") >>> >>> You have to use String.Equals to distinguish between Nothing and an >>> empty >>> string. Personally I find the VB.NET behaviour annoying and would prefer >>> that it worked the same as in C# >>> >>> /claes >>> >>> "David Anton" <DavidAn***@discussions.microsoft.com> wrote in message >>> news:63186DF2-8DE7-4EA4-9927-D6A755AD4596@microsoft.com... >>> > Regarding your first point, VB is even stranger than that: >>> > A string set to Nothng (or uninitialized) is regarded as equal to an >>> > empty >>> > string, but an empty string is *not* regarded as equal to Nothing. C# >>> > is >>> > consistent in this respect: a null string is a null string and an >>> > empty >>> > string is an empty string. >>> > -- >>> > David Anton >>> > www.tangiblesoftwaresolutions.com >>> > Instant C#: VB to C# converter >>> > Instant VB: C# to VB converter >>> > Instant C++: C#/VB to C++ converter >>> > Instant Python: VB to Python converter >>> > >>> > >>> > "Claes Bergefall" wrote: >>> > >>> >> The code you have should work just fine. There are other ways to do >>> >> it as >>> >> well though: >>> >> >>> >> 1. Use the VB.NET "feature" that null and empty string are considered >>> >> equal >>> >> when using the = operator, i.e the following statement: >>> >> If thisString = "" Then >>> >> returns true if thisString is either empty *or* null (beware, this >>> >> does >>> >> not >>> >> work in C#) >>> >> 2. Use the new String.IsNullOrEmpty method (requires .NET 2.0) >>> >> >>> >> /claes >>> >> >>> >> "Neville Lang" <neville@MAPS_ONnjlsoftware.com> wrote in message >>> >> news:ucODy9$9GHA.3348@TK2MSFTNGP03.phx.gbl... >>> >> > Hi all, >>> >> > >>> >> > I am having a memory blank at the moment. I have been writing in C# >>> >> > for >>> >> > a >>> >> > number of years and now need to do something in VB.NET, so forgive >>> >> > me >>> >> > such >>> >> > a primitive question. >>> >> > >>> >> > In C#, I test whether a string has a value or not by the following >>> >> > syntax: >>> >> > >>> >> > if (thisString.Trim() == "") >>> >> > { >>> >> > // if true >>> >> > something() >>> >> > } >>> >> > else >>> >> > { >>> >> > // if false >>> >> > somethingelse() >>> >> > } >>> >> > >>> >> > Now, in VB.NET an equivalent does not seem to work: >>> >> > >>> >> > If thisString.Trim() = "" Then >>> >> > ' if true >>> >> > something() >>> >> > Else >>> >> > ' if false >>> >> > somethingelse() >>> >> > End If >>> >> > >>> >> > I cannot get past a False return for the VB comparison. What is the >>> >> > best >>> >> > method for testing whether a string is empty or null? >>> >> > >>> >> > >>> >> > Regards, >>> >> > Neville Lang >>> >> > >>> >> > >>> >> >>> >> >>> >> >>> >>> >>> > > Jay B. Harlow wrote:
> I find it unfortunate & slightly confusing that C# blurs Equality with What do you mean? The "=" operator is only used for equality, not identity.> Identity with a single operator "=" & "!="; Granted you can still use > Object.ReferenceEquals in C# for Identity... The only time that you should find that confusing, is if you are already confused. If you for example have to references of type object, and they reference strings, comparing them using the "=" operator of course compares the object references, not the strings. If you want to compare the strings, you have to specify that by casting the references. If you are confused about what data types you are using, and what the "=" operator for those datatypes do, of course the result of the operation is also confusing. Göran,
> What do you mean? The "=" operator is only used for equality, not Read the statement again, I was referring to C#:> identity. If you don't override "==" in C# it is used for identity (it reverts to the IL equevilent of Object.ReferenceEquals); if you do override "=" then it would (hopefully) be used for equality. public class Class1 { } Class1 c1 = new Class1(), c2 = c1; Debug.WriteLine(c1 == c2); -- Show quoteHide quoteHope this helps Jay B. Harlow ..NET Application Architect, Enthusiast, & Evangelist T.S. Bradley - http://www.tsbradley.net "Göran Andersson" <gu***@guffa.com> wrote in message news:u%23il6F6%23GHA.3352@TK2MSFTNGP03.phx.gbl... > Jay B. Harlow wrote: >> I find it unfortunate & slightly confusing that C# blurs Equality with >> Identity with a single operator "=" & "!="; Granted you can still use >> Object.ReferenceEquals in C# for Identity... > > What do you mean? The "=" operator is only used for equality, not > identity. > > The only time that you should find that confusing, is if you are already > confused. > > If you for example have to references of type object, and they reference > strings, comparing them using the "=" operator of course compares the > object references, not the strings. If you want to compare the strings, > you have to specify that by casting the references. > > If you are confused about what data types you are using, and what the "=" > operator for those datatypes do, of course the result of the operation is > also confusing. Jay B. Harlow wrote:
Show quoteHide quote > Göran, Of course it does. If you don't override the operator, it's inherited, >> What do you mean? The "=" operator is only used for equality, not >> identity. > Read the statement again, I was referring to C#: > > If you don't override "==" in C# it is used for identity (it reverts to > the IL equevilent of Object.ReferenceEquals); if you do override "=" > then it would (hopefully) be used for equality. > > public class Class1 > { > } > > > Class1 c1 = new Class1(), c2 = c1; > Debug.WriteLine(c1 == c2); > and that is the way that you compare two objects. If you don't like it that way, you can always do it exactly the same way VB does: Debug.WriteLine(Microsoft.VisualBasic.CompilerServices.Operators.CompareObjectEqual(c1,c2)); The method is implemented as: ====== Public Shared Function CompareObjectEqual(ByVal Left As Object, ByVal Right As Object, ByVal TextCompare As Boolean) As Object Dim class1 As CompareClass = Operators.CompareObject2(Left, Right, TextCompare) Select Case class1 Case CompareClass.Unordered Return False Case CompareClass.UserDefined Return Operators.InvokeUserDefinedOperator(UserDefinedOperator.Equal, New Object() { Left, Right }) Case CompareClass.Undefined Throw Operators.GetNoValidOperatorException(UserDefinedOperator.Equal, Left, Right) End Select Return (class1 = CompareClass.Equal) End Function ====== The real work is done in the CompareObject2 method, which is implemented as: ====== Private Shared Function CompareObject2(ByVal Left As Object, ByVal Right As Object, ByVal TextCompare As Boolean) As CompareClass Dim code1 As TypeCode Dim code2 As TypeCode Dim convertible1 As IConvertible = TryCast(Left,IConvertible) If (convertible1 Is Nothing) Then If (Left Is Nothing) Then code1 = TypeCode.Empty Else code1 = TypeCode.Object End If Else code1 = convertible1.GetTypeCode End If Dim convertible2 As IConvertible = TryCast(Right,IConvertible) If (convertible2 Is Nothing) Then If (Right Is Nothing) Then code2 = TypeCode.Empty Else code2 = TypeCode.Object End If Else code2 = convertible2.GetTypeCode End If If (code1 = TypeCode.Object) Then Dim chArray1 As Char() = TryCast(Left,Char()) If ((Not chArray1 Is Nothing) AndAlso (((code2 = TypeCode.String) OrElse (code2 = TypeCode.Empty)) OrElse ((code2 = TypeCode.Object) AndAlso TypeOf Right Is Char()))) Then Left = New String(chArray1) convertible1 = DirectCast(Left, IConvertible) code1 = TypeCode.String End If End If If (code2 = TypeCode.Object) Then Dim chArray2 As Char() = TryCast(Right,Char()) If ((Not chArray2 Is Nothing) AndAlso ((code1 = TypeCode.String) OrElse (code1 = TypeCode.Empty))) Then Right = New String(chArray2) convertible2 = DirectCast(Right, IConvertible) code2 = TypeCode.String End If End If Select Case ((code1 * (TypeCode.String Or TypeCode.Object)) + code2) Case TypeCode.Empty Return CompareClass.Equal Case TypeCode.Boolean Return Operators.CompareBoolean(False, convertible2.ToBoolean(Nothing)) Case TypeCode.Char Return Operators.CompareChar(ChrW(0), convertible2.ToChar(Nothing)) Case TypeCode.SByte Return Operators.CompareInt32(0, convertible2.ToSByte(Nothing)) Case TypeCode.Byte Return Operators.CompareInt32(0, convertible2.ToByte(Nothing)) Case TypeCode.Int16 Return Operators.CompareInt32(0, convertible2.ToInt16(Nothing)) Case TypeCode.UInt16 Return Operators.CompareInt32(0, convertible2.ToUInt16(Nothing)) Case TypeCode.Int32 Return Operators.CompareInt32(0, convertible2.ToInt32(Nothing)) Case TypeCode.UInt32 Return Operators.CompareUInt32(0, convertible2.ToUInt32(Nothing)) Case TypeCode.Int64 Return Operators.CompareInt64(CLng(0), convertible2.ToInt64(Nothing)) Case TypeCode.UInt64 Return Operators.CompareUInt64(0, convertible2.ToUInt64(Nothing)) Case TypeCode.Single Return Operators.CompareSingle(0!, convertible2.ToSingle(Nothing)) Case TypeCode.Double Return Operators.CompareDouble(0, convertible2.ToDouble(Nothing)) Case TypeCode.Decimal Return Operators.CompareDecimal(DirectCast(Decimal.Zero, IConvertible), convertible2) Case TypeCode.DateTime Return Operators.CompareDate(DateTime.MinValue, convertible2.ToDateTime(Nothing)) Case TypeCode.String Return DirectCast(Operators.CompareString(Nothing, convertible2.ToString(Nothing), TextCompare), CompareClass) Case DirectCast(57, TypeCode) Return Operators.CompareBoolean(convertible1.ToBoolean(Nothing), False) Case DirectCast(60, TypeCode) Return Operators.CompareBoolean(convertible1.ToBoolean(Nothing), convertible2.ToBoolean(Nothing)) Case DirectCast(62, TypeCode) Return Operators.CompareInt32(Operators.ToVBBool(convertible1), convertible2.ToSByte(Nothing)) Case DirectCast(63, TypeCode), DirectCast(64, TypeCode) Return Operators.CompareInt32(Operators.ToVBBool(convertible1), convertible2.ToInt16(Nothing)) Case DirectCast(65, TypeCode), DirectCast(66, TypeCode) Return Operators.CompareInt32(Operators.ToVBBool(convertible1), convertible2.ToInt32(Nothing)) Case DirectCast(67, TypeCode), DirectCast(68, TypeCode) Return Operators.CompareInt64(CLng(Operators.ToVBBool(convertible1)), convertible2.ToInt64(Nothing)) Case DirectCast(69, TypeCode), DirectCast(72, TypeCode) Return Operators.CompareDecimal(Operators.ToVBBoolConv(convertible1), convertible2) Case DirectCast(70, TypeCode) Return Operators.CompareSingle(CSng(Operators.ToVBBool(convertible1)), convertible2.ToSingle(Nothing)) Case DirectCast(71, TypeCode) Return Operators.CompareDouble(CDbl(Operators.ToVBBool(convertible1)), convertible2.ToDouble(Nothing)) Case DirectCast(75, TypeCode) Return Operators.CompareBoolean(convertible1.ToBoolean(Nothing), Conversions.ToBoolean(convertible2.ToString(Nothing))) Case DirectCast(76, TypeCode) Return Operators.CompareChar(convertible1.ToChar(Nothing), ChrW(0)) Case DirectCast(80, TypeCode) Return Operators.CompareChar(convertible1.ToChar(Nothing), convertible2.ToChar(Nothing)) Case DirectCast(94, TypeCode), DirectCast(346, TypeCode), DirectCast(360, TypeCode) Return DirectCast(Operators.CompareString(convertible1.ToString(Nothing), convertible2.ToString(Nothing), TextCompare), CompareClass) Case DirectCast(95, TypeCode) Return Operators.CompareInt32(convertible1.ToSByte(Nothing), 0) Case DirectCast(98, TypeCode) Return Operators.CompareInt32(convertible1.ToSByte(Nothing), Operators.ToVBBool(convertible2)) Case DirectCast(100, TypeCode) Return Operators.CompareInt32(convertible1.ToSByte(Nothing), convertible2.ToSByte(Nothing)) Case DirectCast(101, TypeCode), DirectCast(102, TypeCode), DirectCast(119, TypeCode), DirectCast(121, TypeCode), DirectCast(138, TypeCode), DirectCast(139, TypeCode), DirectCast(140, TypeCode) Return Operators.CompareInt32(convertible1.ToInt16(Nothing), convertible2.ToInt16(Nothing)) Case DirectCast(103, TypeCode), DirectCast(104, TypeCode), DirectCast(123, TypeCode), DirectCast(141, TypeCode), DirectCast(142, TypeCode), DirectCast(157, TypeCode), DirectCast(159, TypeCode), DirectCast(161, TypeCode), DirectCast(176, TypeCode), DirectCast(177, TypeCode), DirectCast(178, TypeCode), DirectCast(179, TypeCode), DirectCast(180, TypeCode) Return Operators.CompareInt32(convertible1.ToInt32(Nothing), convertible2.ToInt32(Nothing)) Case DirectCast(105, TypeCode), DirectCast(106, TypeCode), DirectCast(125, TypeCode), DirectCast(143, TypeCode), DirectCast(144, TypeCode), DirectCast(163, TypeCode), DirectCast(181, TypeCode), DirectCast(182, TypeCode), DirectCast(195, TypeCode), DirectCast(197, TypeCode), DirectCast(199, TypeCode), DirectCast(201, TypeCode), DirectCast(214, TypeCode), DirectCast(215, TypeCode), DirectCast(216, TypeCode), DirectCast(217, TypeCode), DirectCast(218, TypeCode), DirectCast(219, TypeCode), DirectCast(220, TypeCode) Return Operators.CompareInt64(convertible1.ToInt64(Nothing), convertible2.ToInt64(Nothing)) Case DirectCast(107, TypeCode), DirectCast(110, TypeCode), DirectCast(129, TypeCode), DirectCast(145, TypeCode), DirectCast(148, TypeCode), DirectCast(167, TypeCode), DirectCast(183, TypeCode), DirectCast(186, TypeCode), DirectCast(205, TypeCode), DirectCast(221, TypeCode), DirectCast(224, TypeCode), DirectCast(233, TypeCode), DirectCast(235, TypeCode), DirectCast(237, TypeCode), DirectCast(239, TypeCode), DirectCast(243, TypeCode), DirectCast(290, TypeCode), DirectCast(291, TypeCode), DirectCast(292, TypeCode), DirectCast(293, TypeCode), DirectCast(294, TypeCode), DirectCast(295, TypeCode), DirectCast(296, TypeCode), DirectCast(297, TypeCode), DirectCast(300, TypeCode) Return Operators.CompareDecimal(convertible1, convertible2) Case DirectCast(108, TypeCode), DirectCast(127, TypeCode), DirectCast(146, TypeCode), DirectCast(165, TypeCode), DirectCast(184, TypeCode), DirectCast(203, TypeCode), DirectCast(222, TypeCode), DirectCast(241, TypeCode), DirectCast(252, TypeCode), DirectCast(253, TypeCode), DirectCast(254, TypeCode), DirectCast(255, TypeCode), DirectCast(256, TypeCode), DirectCast(257, TypeCode), DirectCast(258, TypeCode), DirectCast(259, TypeCode), DirectCast(260, TypeCode), DirectCast(262, TypeCode), DirectCast(298, TypeCode) Return Operators.CompareSingle(convertible1.ToSingle(Nothing), convertible2.ToSingle(Nothing)) Case DirectCast(109, TypeCode), DirectCast(128, TypeCode), DirectCast(147, TypeCode), DirectCast(166, TypeCode), DirectCast(185, TypeCode), DirectCast(204, TypeCode), DirectCast(223, TypeCode), DirectCast(242, TypeCode), DirectCast(261, TypeCode), DirectCast(271, TypeCode), DirectCast(272, TypeCode), DirectCast(273, TypeCode), DirectCast(274, TypeCode), DirectCast(275, TypeCode), DirectCast(276, TypeCode), DirectCast(277, TypeCode), DirectCast(278, TypeCode), DirectCast(279, TypeCode), DirectCast(280, TypeCode), DirectCast(281, TypeCode), DirectCast(299, TypeCode) Return Operators.CompareDouble(convertible1.ToDouble(Nothing), convertible2.ToDouble(Nothing)) Case DirectCast(113, TypeCode), DirectCast(132, TypeCode), DirectCast(151, TypeCode), DirectCast(170, TypeCode), DirectCast(189, TypeCode), DirectCast(208, TypeCode), DirectCast(227, TypeCode), DirectCast(246, TypeCode), DirectCast(265, TypeCode), DirectCast(284, TypeCode), DirectCast(303, TypeCode) Return Operators.CompareDouble(convertible1.ToDouble(Nothing), Conversions.ToDouble(convertible2.ToString(Nothing))) Case DirectCast(114, TypeCode) Return Operators.CompareInt32(convertible1.ToByte(Nothing), 0) Case DirectCast(117, TypeCode) Return Operators.CompareInt32(convertible1.ToInt16(Nothing), Operators.ToVBBool(convertible2)) Case DirectCast(120, TypeCode) Return Operators.CompareInt32(convertible1.ToByte(Nothing), convertible2.ToByte(Nothing)) Case DirectCast(122, TypeCode), DirectCast(158, TypeCode), DirectCast(160, TypeCode) Return Operators.CompareInt32(convertible1.ToUInt16(Nothing), convertible2.ToUInt16(Nothing)) Case DirectCast(124, TypeCode), DirectCast(162, TypeCode), DirectCast(196, TypeCode), DirectCast(198, TypeCode), DirectCast(200, TypeCode) Return Operators.CompareUInt32(convertible1.ToUInt32(Nothing), convertible2.ToUInt32(Nothing)) Case DirectCast(126, TypeCode), DirectCast(164, TypeCode), DirectCast(202, TypeCode), DirectCast(234, TypeCode), DirectCast(236, TypeCode), DirectCast(238, TypeCode), DirectCast(240, TypeCode) Return Operators.CompareUInt64(convertible1.ToUInt64(Nothing), convertible2.ToUInt64(Nothing)) Case DirectCast(133, TypeCode) Return Operators.CompareInt32(convertible1.ToInt16(Nothing), 0) Case DirectCast(136, TypeCode) Return Operators.CompareInt32(convertible1.ToInt16(Nothing), Operators.ToVBBool(convertible2)) Case DirectCast(152, TypeCode) Return Operators.CompareInt32(convertible1.ToUInt16(Nothing), 0) Case DirectCast(155, TypeCode) Return Operators.CompareInt32(convertible1.ToInt32(Nothing), Operators.ToVBBool(convertible2)) Case DirectCast(171, TypeCode) Return Operators.CompareInt32(convertible1.ToInt32(Nothing), 0) Case DirectCast(174, TypeCode) Return Operators.CompareInt32(convertible1.ToInt32(Nothing), Operators.ToVBBool(convertible2)) Case DirectCast(190, TypeCode) Return Operators.CompareUInt32(convertible1.ToUInt32(Nothing), 0) Case DirectCast(193, TypeCode) Return Operators.CompareInt64(convertible1.ToInt64(Nothing), CLng(Operators.ToVBBool(convertible2))) Case DirectCast(209, TypeCode) Return Operators.CompareInt64(convertible1.ToInt64(Nothing), CLng(0)) Case DirectCast(212, TypeCode) Return Operators.CompareInt64(convertible1.ToInt64(Nothing), CLng(Operators.ToVBBool(convertible2))) Case DirectCast(228, TypeCode) Return Operators.CompareUInt64(convertible1.ToUInt64(Nothing), 0) Case DirectCast(231, TypeCode) Return Operators.CompareDecimal(convertible1, Operators.ToVBBoolConv(convertible2)) Case DirectCast(247, TypeCode) Return Operators.CompareSingle(convertible1.ToSingle(Nothing), 0!) Case DirectCast(250, TypeCode) Return Operators.CompareSingle(convertible1.ToSingle(Nothing), CSng(Operators.ToVBBool(convertible2))) Case DirectCast(266, TypeCode) Return Operators.CompareDouble(convertible1.ToDouble(Nothing), 0) Case DirectCast(269, TypeCode) Return Operators.CompareDouble(convertible1.ToDouble(Nothing), CDbl(Operators.ToVBBool(convertible2))) Case DirectCast(285, TypeCode) Return Operators.CompareDecimal(convertible1, DirectCast(Decimal.Zero, IConvertible)) Case DirectCast(288, TypeCode) Return Operators.CompareDecimal(convertible1, Operators.ToVBBoolConv(convertible2)) Case DirectCast(304, TypeCode) Return Operators.CompareDate(convertible1.ToDateTime(Nothing), DateTime.MinValue) Case DirectCast(320, TypeCode) Return Operators.CompareDate(convertible1.ToDateTime(Nothing), convertible2.ToDateTime(Nothing)) Case DirectCast(322, TypeCode) Return Operators.CompareDate(convertible1.ToDateTime(Nothing), Conversions.ToDate(convertible2.ToString(Nothing))) Case DirectCast(342, TypeCode) Return DirectCast(Operators.CompareString(convertible1.ToString(Nothing), Nothing, TextCompare), CompareClass) Case DirectCast(345, TypeCode) Return Operators.CompareBoolean(Conversions.ToBoolean(convertible1.ToString(Nothing)), convertible2.ToBoolean(Nothing)) Case DirectCast(347, TypeCode), DirectCast(348, TypeCode), DirectCast(349, TypeCode), DirectCast(350, TypeCode), DirectCast(351, TypeCode), DirectCast(352, TypeCode), DirectCast(353, TypeCode), DirectCast(354, TypeCode), DirectCast(355, TypeCode), DirectCast(356, TypeCode), DirectCast(357, TypeCode) Return Operators.CompareDouble(Conversions.ToDouble(convertible1.ToString(Nothing)), convertible2.ToDouble(Nothing)) Case DirectCast(358, TypeCode) Return Operators.CompareDate(Conversions.ToDate(convertible1.ToString(Nothing)), convertible2.ToDateTime(Nothing)) End Select If ((code1 <> TypeCode.Object) AndAlso (code2 <> TypeCode.Object)) Then Return CompareClass.Undefined End If Return CompareClass.UserDefined End Function ====== Yeah, that is much better. ;) Göran,
> Of course it does. If you don't override the operator, it's inherited, and "Of course it does" what? Are you now agreeing with me that C# uses the "==" > that is the way that you compare two objects. operator for both equality & identity? Unlike VB that has separate operators for equality & identity? > If you don't like it that way, you can always do it exactly the same way As I stated earlier I can use "==" for (blurred) equality/identity in C# or > VB does: use Object.ReferenceEquals if I explicitly need identity in C#. I really don't see the connection of a VB equality routine will help with Identity in C#! -- Show quoteHide quoteHope this helps Jay B. Harlow ..NET Application Architect, Enthusiast, & Evangelist T.S. Bradley - http://www.tsbradley.net "Göran Andersson" <gu***@guffa.com> wrote in message news:eGGJdVT$GHA.3344@TK2MSFTNGP03.phx.gbl... > Jay B. Harlow wrote: >> Göran, >>> What do you mean? The "=" operator is only used for equality, not >>> identity. >> Read the statement again, I was referring to C#: >> >> If you don't override "==" in C# it is used for identity (it reverts to >> the IL equevilent of Object.ReferenceEquals); if you do override "=" then >> it would (hopefully) be used for equality. >> >> public class Class1 >> { >> } >> >> >> Class1 c1 = new Class1(), c2 = c1; >> Debug.WriteLine(c1 == c2); >> > > Of course it does. If you don't override the operator, it's inherited, and > that is the way that you compare two objects. > > If you don't like it that way, you can always do it exactly the same way > VB does: > > Debug.WriteLine(Microsoft.VisualBasic.CompilerServices.Operators.CompareObjectEqual(c1,c2)); > > The method is implemented as: > > ====== > > Public Shared Function CompareObjectEqual(ByVal Left As Object, ByVal > Right As Object, ByVal TextCompare As Boolean) As Object > Dim class1 As CompareClass = Operators.CompareObject2(Left, Right, > TextCompare) > Select Case class1 > Case CompareClass.Unordered > Return False > Case CompareClass.UserDefined > Return > Operators.InvokeUserDefinedOperator(UserDefinedOperator.Equal, New > Object() { Left, Right }) > Case CompareClass.Undefined > Throw > Operators.GetNoValidOperatorException(UserDefinedOperator.Equal, Left, > Right) > End Select > Return (class1 = CompareClass.Equal) > End Function > > ====== > > The real work is done in the CompareObject2 method, which is implemented > as: > > ====== > > Private Shared Function CompareObject2(ByVal Left As Object, ByVal Right > As Object, ByVal TextCompare As Boolean) As CompareClass > Dim code1 As TypeCode > Dim code2 As TypeCode > Dim convertible1 As IConvertible = TryCast(Left,IConvertible) > If (convertible1 Is Nothing) Then > If (Left Is Nothing) Then > code1 = TypeCode.Empty > Else > code1 = TypeCode.Object > End If > Else > code1 = convertible1.GetTypeCode > End If > Dim convertible2 As IConvertible = TryCast(Right,IConvertible) > If (convertible2 Is Nothing) Then > If (Right Is Nothing) Then > code2 = TypeCode.Empty > Else > code2 = TypeCode.Object > End If > Else > code2 = convertible2.GetTypeCode > End If > If (code1 = TypeCode.Object) Then > Dim chArray1 As Char() = TryCast(Left,Char()) > If ((Not chArray1 Is Nothing) AndAlso (((code2 = > TypeCode.String) OrElse (code2 = TypeCode.Empty)) OrElse ((code2 = > TypeCode.Object) AndAlso TypeOf Right Is Char()))) Then > Left = New String(chArray1) > convertible1 = DirectCast(Left, IConvertible) > code1 = TypeCode.String > End If > End If > If (code2 = TypeCode.Object) Then > Dim chArray2 As Char() = TryCast(Right,Char()) > If ((Not chArray2 Is Nothing) AndAlso ((code1 = > TypeCode.String) OrElse (code1 = TypeCode.Empty))) Then > Right = New String(chArray2) > convertible2 = DirectCast(Right, IConvertible) > code2 = TypeCode.String > End If > End If > Select Case ((code1 * (TypeCode.String Or TypeCode.Object)) + code2) > Case TypeCode.Empty > Return CompareClass.Equal > Case TypeCode.Boolean > Return Operators.CompareBoolean(False, > convertible2.ToBoolean(Nothing)) > Case TypeCode.Char > Return Operators.CompareChar(ChrW(0), > convertible2.ToChar(Nothing)) > Case TypeCode.SByte > Return Operators.CompareInt32(0, > convertible2.ToSByte(Nothing)) > Case TypeCode.Byte > Return Operators.CompareInt32(0, > convertible2.ToByte(Nothing)) > Case TypeCode.Int16 > Return Operators.CompareInt32(0, > convertible2.ToInt16(Nothing)) > Case TypeCode.UInt16 > Return Operators.CompareInt32(0, > convertible2.ToUInt16(Nothing)) > Case TypeCode.Int32 > Return Operators.CompareInt32(0, > convertible2.ToInt32(Nothing)) > Case TypeCode.UInt32 > Return Operators.CompareUInt32(0, > convertible2.ToUInt32(Nothing)) > Case TypeCode.Int64 > Return Operators.CompareInt64(CLng(0), > convertible2.ToInt64(Nothing)) > Case TypeCode.UInt64 > Return Operators.CompareUInt64(0, > convertible2.ToUInt64(Nothing)) > Case TypeCode.Single > Return Operators.CompareSingle(0!, > convertible2.ToSingle(Nothing)) > Case TypeCode.Double > Return Operators.CompareDouble(0, > convertible2.ToDouble(Nothing)) > Case TypeCode.Decimal > Return Operators.CompareDecimal(DirectCast(Decimal.Zero, > IConvertible), convertible2) > Case TypeCode.DateTime > Return Operators.CompareDate(DateTime.MinValue, > convertible2.ToDateTime(Nothing)) > Case TypeCode.String > Return DirectCast(Operators.CompareString(Nothing, > convertible2.ToString(Nothing), TextCompare), CompareClass) > Case DirectCast(57, TypeCode) > Return > Operators.CompareBoolean(convertible1.ToBoolean(Nothing), False) > Case DirectCast(60, TypeCode) > Return > Operators.CompareBoolean(convertible1.ToBoolean(Nothing), > convertible2.ToBoolean(Nothing)) > Case DirectCast(62, TypeCode) > Return > Operators.CompareInt32(Operators.ToVBBool(convertible1), > convertible2.ToSByte(Nothing)) > Case DirectCast(63, TypeCode), DirectCast(64, TypeCode) > Return > Operators.CompareInt32(Operators.ToVBBool(convertible1), > convertible2.ToInt16(Nothing)) > Case DirectCast(65, TypeCode), DirectCast(66, TypeCode) > Return > Operators.CompareInt32(Operators.ToVBBool(convertible1), > convertible2.ToInt32(Nothing)) > Case DirectCast(67, TypeCode), DirectCast(68, TypeCode) > Return > Operators.CompareInt64(CLng(Operators.ToVBBool(convertible1)), > convertible2.ToInt64(Nothing)) > Case DirectCast(69, TypeCode), DirectCast(72, TypeCode) > Return > Operators.CompareDecimal(Operators.ToVBBoolConv(convertible1), > convertible2) > Case DirectCast(70, TypeCode) > Return > Operators.CompareSingle(CSng(Operators.ToVBBool(convertible1)), > convertible2.ToSingle(Nothing)) > Case DirectCast(71, TypeCode) > Return > Operators.CompareDouble(CDbl(Operators.ToVBBool(convertible1)), > convertible2.ToDouble(Nothing)) > Case DirectCast(75, TypeCode) > Return > Operators.CompareBoolean(convertible1.ToBoolean(Nothing), > Conversions.ToBoolean(convertible2.ToString(Nothing))) > Case DirectCast(76, TypeCode) > Return > Operators.CompareChar(convertible1.ToChar(Nothing), ChrW(0)) > Case DirectCast(80, TypeCode) > Return > Operators.CompareChar(convertible1.ToChar(Nothing), > convertible2.ToChar(Nothing)) > Case DirectCast(94, TypeCode), DirectCast(346, TypeCode), > DirectCast(360, TypeCode) > Return > DirectCast(Operators.CompareString(convertible1.ToString(Nothing), > convertible2.ToString(Nothing), TextCompare), CompareClass) > Case DirectCast(95, TypeCode) > Return > Operators.CompareInt32(convertible1.ToSByte(Nothing), 0) > Case DirectCast(98, TypeCode) > Return > Operators.CompareInt32(convertible1.ToSByte(Nothing), > Operators.ToVBBool(convertible2)) > Case DirectCast(100, TypeCode) > Return > Operators.CompareInt32(convertible1.ToSByte(Nothing), > convertible2.ToSByte(Nothing)) > Case DirectCast(101, TypeCode), DirectCast(102, TypeCode), > DirectCast(119, TypeCode), DirectCast(121, TypeCode), DirectCast(138, > TypeCode), DirectCast(139, TypeCode), DirectCast(140, TypeCode) > Return > Operators.CompareInt32(convertible1.ToInt16(Nothing), > convertible2.ToInt16(Nothing)) > Case DirectCast(103, TypeCode), DirectCast(104, TypeCode), > DirectCast(123, TypeCode), DirectCast(141, TypeCode), DirectCast(142, > TypeCode), DirectCast(157, TypeCode), DirectCast(159, TypeCode), > DirectCast(161, TypeCode), DirectCast(176, TypeCode), DirectCast(177, > TypeCode), DirectCast(178, TypeCode), DirectCast(179, TypeCode), > DirectCast(180, TypeCode) > Return > Operators.CompareInt32(convertible1.ToInt32(Nothing), > convertible2.ToInt32(Nothing)) > Case DirectCast(105, TypeCode), DirectCast(106, TypeCode), > DirectCast(125, TypeCode), DirectCast(143, TypeCode), DirectCast(144, > TypeCode), DirectCast(163, TypeCode), DirectCast(181, TypeCode), > DirectCast(182, TypeCode), DirectCast(195, TypeCode), DirectCast(197, > TypeCode), DirectCast(199, TypeCode), DirectCast(201, TypeCode), > DirectCast(214, TypeCode), DirectCast(215, TypeCode), DirectCast(216, > TypeCode), DirectCast(217, TypeCode), DirectCast(218, TypeCode), > DirectCast(219, TypeCode), DirectCast(220, TypeCode) > Return > Operators.CompareInt64(convertible1.ToInt64(Nothing), > convertible2.ToInt64(Nothing)) > Case DirectCast(107, TypeCode), DirectCast(110, TypeCode), > DirectCast(129, TypeCode), DirectCast(145, TypeCode), DirectCast(148, > TypeCode), DirectCast(167, TypeCode), DirectCast(183, TypeCode), > DirectCast(186, TypeCode), DirectCast(205, TypeCode), DirectCast(221, > TypeCode), DirectCast(224, TypeCode), DirectCast(233, TypeCode), > DirectCast(235, TypeCode), DirectCast(237, TypeCode), DirectCast(239, > TypeCode), DirectCast(243, TypeCode), DirectCast(290, TypeCode), > DirectCast(291, TypeCode), DirectCast(292, TypeCode), DirectCast(293, > TypeCode), DirectCast(294, TypeCode), DirectCast(295, TypeCode), > DirectCast(296, TypeCode), DirectCast(297, TypeCode), DirectCast(300, > TypeCode) > Return Operators.CompareDecimal(convertible1, > convertible2) > Case DirectCast(108, TypeCode), DirectCast(127, TypeCode), > DirectCast(146, TypeCode), DirectCast(165, TypeCode), DirectCast(184, > TypeCode), DirectCast(203, TypeCode), DirectCast(222, TypeCode), > DirectCast(241, TypeCode), DirectCast(252, TypeCode), DirectCast(253, > TypeCode), DirectCast(254, TypeCode), DirectCast(255, TypeCode), > DirectCast(256, TypeCode), DirectCast(257, TypeCode), DirectCast(258, > TypeCode), DirectCast(259, TypeCode), DirectCast(260, TypeCode), > DirectCast(262, TypeCode), DirectCast(298, TypeCode) > Return > Operators.CompareSingle(convertible1.ToSingle(Nothing), > convertible2.ToSingle(Nothing)) > Case DirectCast(109, TypeCode), DirectCast(128, TypeCode), > DirectCast(147, TypeCode), DirectCast(166, TypeCode), DirectCast(185, > TypeCode), DirectCast(204, TypeCode), DirectCast(223, TypeCode), > DirectCast(242, TypeCode), DirectCast(261, TypeCode), DirectCast(271, > TypeCode), DirectCast(272, TypeCode), DirectCast(273, TypeCode), > DirectCast(274, TypeCode), DirectCast(275, TypeCode), DirectCast(276, > TypeCode), DirectCast(277, TypeCode), DirectCast(278, TypeCode), > DirectCast(279, TypeCode), DirectCast(280, TypeCode), DirectCast(281, > TypeCode), DirectCast(299, TypeCode) > Return > Operators.CompareDouble(convertible1.ToDouble(Nothing), > convertible2.ToDouble(Nothing)) > Case DirectCast(113, TypeCode), DirectCast(132, TypeCode), > DirectCast(151, TypeCode), DirectCast(170, TypeCode), DirectCast(189, > TypeCode), DirectCast(208, TypeCode), DirectCast(227, TypeCode), > DirectCast(246, TypeCode), DirectCast(265, TypeCode), DirectCast(284, > TypeCode), DirectCast(303, TypeCode) > Return > Operators.CompareDouble(convertible1.ToDouble(Nothing), > Conversions.ToDouble(convertible2.ToString(Nothing))) > Case DirectCast(114, TypeCode) > Return > Operators.CompareInt32(convertible1.ToByte(Nothing), 0) > Case DirectCast(117, TypeCode) > Return > Operators.CompareInt32(convertible1.ToInt16(Nothing), > Operators.ToVBBool(convertible2)) > Case DirectCast(120, TypeCode) > Return > Operators.CompareInt32(convertible1.ToByte(Nothing), > convertible2.ToByte(Nothing)) > Case DirectCast(122, TypeCode), DirectCast(158, TypeCode), > DirectCast(160, TypeCode) > Return > Operators.CompareInt32(convertible1.ToUInt16(Nothing), > convertible2.ToUInt16(Nothing)) > Case DirectCast(124, TypeCode), DirectCast(162, TypeCode), > DirectCast(196, TypeCode), DirectCast(198, TypeCode), DirectCast(200, > TypeCode) > Return > Operators.CompareUInt32(convertible1.ToUInt32(Nothing), > convertible2.ToUInt32(Nothing)) > Case DirectCast(126, TypeCode), DirectCast(164, TypeCode), > DirectCast(202, TypeCode), DirectCast(234, TypeCode), DirectCast(236, > TypeCode), DirectCast(238, TypeCode), DirectCast(240, TypeCode) > Return > Operators.CompareUInt64(convertible1.ToUInt64(Nothing), > convertible2.ToUInt64(Nothing)) > Case DirectCast(133, TypeCode) > Return > Operators.CompareInt32(convertible1.ToInt16(Nothing), 0) > Case DirectCast(136, TypeCode) > Return > Operators.CompareInt32(convertible1.ToInt16(Nothing), > Operators.ToVBBool(convertible2)) > Case DirectCast(152, TypeCode) > Return > Operators.CompareInt32(convertible1.ToUInt16(Nothing), 0) > Case DirectCast(155, TypeCode) > Return > Operators.CompareInt32(convertible1.ToInt32(Nothing), > Operators.ToVBBool(convertible2)) > Case DirectCast(171, TypeCode) > Return > Operators.CompareInt32(convertible1.ToInt32(Nothing), 0) > Case DirectCast(174, TypeCode) > Return > Operators.CompareInt32(convertible1.ToInt32(Nothing), > Operators.ToVBBool(convertible2)) > Case DirectCast(190, TypeCode) > Return > Operators.CompareUInt32(convertible1.ToUInt32(Nothing), 0) > Case DirectCast(193, TypeCode) > Return > Operators.CompareInt64(convertible1.ToInt64(Nothing), > CLng(Operators.ToVBBool(convertible2))) > Case DirectCast(209, TypeCode) > Return > Operators.CompareInt64(convertible1.ToInt64(Nothing), CLng(0)) > Case DirectCast(212, TypeCode) > Return > Operators.CompareInt64(convertible1.ToInt64(Nothing), > CLng(Operators.ToVBBool(convertible2))) > Case DirectCast(228, TypeCode) > Return > Operators.CompareUInt64(convertible1.ToUInt64(Nothing), 0) > Case DirectCast(231, TypeCode) > Return Operators.CompareDecimal(convertible1, > Operators.ToVBBoolConv(convertible2)) > Case DirectCast(247, TypeCode) > Return > Operators.CompareSingle(convertible1.ToSingle(Nothing), 0!) > Case DirectCast(250, TypeCode) > Return > Operators.CompareSingle(convertible1.ToSingle(Nothing), > CSng(Operators.ToVBBool(convertible2))) > Case DirectCast(266, TypeCode) > Return > Operators.CompareDouble(convertible1.ToDouble(Nothing), 0) > Case DirectCast(269, TypeCode) > Return > Operators.CompareDouble(convertible1.ToDouble(Nothing), > CDbl(Operators.ToVBBool(convertible2))) > Case DirectCast(285, TypeCode) > Return Operators.CompareDecimal(convertible1, > DirectCast(Decimal.Zero, IConvertible)) > Case DirectCast(288, TypeCode) > Return Operators.CompareDecimal(convertible1, > Operators.ToVBBoolConv(convertible2)) > Case DirectCast(304, TypeCode) > Return > Operators.CompareDate(convertible1.ToDateTime(Nothing), DateTime.MinValue) > Case DirectCast(320, TypeCode) > Return > Operators.CompareDate(convertible1.ToDateTime(Nothing), > convertible2.ToDateTime(Nothing)) > Case DirectCast(322, TypeCode) > Return > Operators.CompareDate(convertible1.ToDateTime(Nothing), > Conversions.ToDate(convertible2.ToString(Nothing))) > Case DirectCast(342, TypeCode) > Return > DirectCast(Operators.CompareString(convertible1.ToString(Nothing), > Nothing, TextCompare), CompareClass) > Case DirectCast(345, TypeCode) > Return > Operators.CompareBoolean(Conversions.ToBoolean(convertible1.ToString(Nothing)), > convertible2.ToBoolean(Nothing)) > Case DirectCast(347, TypeCode), DirectCast(348, TypeCode), > DirectCast(349, TypeCode), DirectCast(350, TypeCode), DirectCast(351, > TypeCode), DirectCast(352, TypeCode), DirectCast(353, TypeCode), > DirectCast(354, TypeCode), DirectCast(355, TypeCode), DirectCast(356, > TypeCode), DirectCast(357, TypeCode) > Return > Operators.CompareDouble(Conversions.ToDouble(convertible1.ToString(Nothing)), > convertible2.ToDouble(Nothing)) > Case DirectCast(358, TypeCode) > Return > Operators.CompareDate(Conversions.ToDate(convertible1.ToString(Nothing)), > convertible2.ToDateTime(Nothing)) > End Select > If ((code1 <> TypeCode.Object) AndAlso (code2 <> TypeCode.Object)) > Then > Return CompareClass.Undefined > End If > Return CompareClass.UserDefined > End Function > > ====== > > Yeah, that is much better. ;) Jay B. Harlow wrote:
> Göran, The operator is used for equality. For the Object class it's the >> Of course it does. If you don't override the operator, it's inherited, >> and that is the way that you compare two objects. > "Of course it does" what? Are you now agreeing with me that C# uses the > "==" operator for both equality & identity? Unlike VB that has separate > operators for equality & identity? references that are compared, which gives that it works the same as comparing identity. >> If you don't like it that way, you can always do it exactly the same Maybe I wasn't clear enough; that's the method that is called when you >> way VB does: > As I stated earlier I can use "==" for (blurred) equality/identity in C# > or use Object.ReferenceEquals if I explicitly need identity in C#. I > really don't see the connection of a VB equality routine will help with > Identity in C#! use the "=" operator in VB. Göran,
> which gives that it works the same as comparing identity. It sounds like we're quibbling over semantics. ;-)If it looks like a rose, smells like a rose, tastes like a rose, feels like a rose; I would say it must be a rose! If it "works the same as comparing identity", would that not be the same as stating is it identity? It does in my book! ;-) -- Show quoteHide quoteHope this helps Jay B. Harlow ..NET Application Architect, Enthusiast, & Evangelist T.S. Bradley - http://www.tsbradley.net "Göran Andersson" <gu***@guffa.com> wrote in message news:eAaO7De$GHA.1556@TK2MSFTNGP03.phx.gbl... > Jay B. Harlow wrote: >> Göran, >>> Of course it does. If you don't override the operator, it's inherited, >>> and that is the way that you compare two objects. >> "Of course it does" what? Are you now agreeing with me that C# uses the >> "==" operator for both equality & identity? Unlike VB that has separate >> operators for equality & identity? > > The operator is used for equality. For the Object class it's the > references that are compared, which gives that it works the same as > comparing identity. > >>> If you don't like it that way, you can always do it exactly the same way >>> VB does: >> As I stated earlier I can use "==" for (blurred) equality/identity in C# >> or use Object.ReferenceEquals if I explicitly need identity in C#. I >> really don't see the connection of a VB equality routine will help with >> Identity in C#! > > Maybe I wasn't clear enough; that's the method that is called when you use > the "=" operator in VB. Jay B. Harlow wrote:
> Göran, Yes, it's semantics, that's why it isn't a rose just because it happens >> which gives that it works the same as comparing identity. > It sounds like we're quibbling over semantics. ;-) > > If it looks like a rose, smells like a rose, tastes like a rose, feels > like a rose; I would say it must be a rose! > > If it "works the same as comparing identity", would that not be the same > as stating is it identity? It does in my book! ;-) > to look like a rose from a certain angle. ;) Just because it works like identity doesn't mean that it is identity. If you have two integer that have the value two, and multiply them, you get the result four. If you add them together you also get the result four. That however does not mean that multiplying and adding is the same thing in this case. They are still completely different operations eventhough they give the same result. Anyway, the difference between VB.NET and C# isn't really how comparison works, but what comparison is used. While the C# compiler actually uses the operator supplied by the Object class to compare Object instances, VB uses the Microsoft.VisualBasic.CompilerServices.Operators.CompareObjectEqual method instead. Göran,
> Yes, it's semantics, that's why it isn't a rose just because it happens to OK, you haven't convinced me. :-|> look like a rose from a certain angle. ;) > Just because it works like identity doesn't mean that it is identity. OK, reading the C# specification states:<quote src="http://msdn2.microsoft.com/en-us/library/53k8ybth.aspx"> For predefined value types, the equality operator (==) returns true if the values of its operands are equal, false otherwise. For reference types other than string, == returns true if its two operands refer to the same object. For the string type, == compares the values of the strings. </quote> Last I checked Identity equality means "two operands refer to the same object" as their identity is the reference itself. > Anyway, the difference between VB.NET and C# isn't really how comparison Now we're getting someplace.> works, but what comparison is used. VB "IS" operator compiles to an ceq IL opcode for any reference type, not just System.Object variables. C# "==" operator compiles to the same ceq IL opcode for any reference type, not just System.Object variables, unless of course that reference type overloads the "==" operator. As you may know you need VB 2005 to gain the use of overloaded operators. In which case C#'s overloaded "==" operator is VB's overloaded "=" comparison operator. Neither VB nor C# allows you to overload the assignment operator itself. VB does not allow you to overload the IS operator. > While the C# compiler actually uses the operator supplied by the Object I'm sorry Göran; System.Object doesn't offer any operators!> class to compare Object instances, VB uses the > Microsoft.VisualBasic.CompilerServices.Operators.CompareObjectEqual As I stated earlier C# uses an IL opcode, the same opcode that is used (by both VB & C#) for equality with types such as Int32, Byte, Double & other "predefined value types". Further C# uses the exactly same opcode for any reference type if you do not overload the == operator! Such as my example of Class1! Compile and check out the IL for the sample I gave earlier: public class Class1 { } Class1 c1 = new Class1(), c2 = c1; Debug.WriteLine(c1 == c2); Try the same in VB, with Option Strict On and with Option Strict Off Public Class Class1 End Class Dim c1 As New Class1(), c2 = c1 Debug.WriteLine(c1 = c2) Debug.WriteLine(c1 Is c2) Try adding an overloaded equality operator in both C# & VB public class Class1 { public static bool operator ==(Class1 c1, Class1 c2) { } public static bool operator !=(Class1 c1, Class1 c2) { } } Public Class Class1 Public Shared Operator =(ByVal c1 As Class1, ByVal c2 As Class1) As Boolean End Operator Public Shared Operator <>(ByVal c1 As Class1, ByVal c2 As Class1) As Boolean End Operator End Class Compile both & examine the IL again. Try the above for any number of reference types (Class), and any number of value types (struct, Structure). As far as I can tell CompareObjectEqual is only used when you have Option Strict Off and only if both operands are System.Object types. If you have a case where CompareObjectEqual is used with Option Strict On or used for types other then System.Object I would love to see it! To maximize compile errors over obscure runtime errors I normally use Option Strict On. With Option Strict On the "=" comparison operator causes a compile error in VB unless the type overloads the "=" operator. This means that Int32, Byte, Double are allowed as are any types that VB implicitly defines the operator for (such as Date) or the developer who defined the type explicitly define the operator (such as TimeSpan). Some types, such as String VB has defined its own equality operator that overrides String's = operator. Option Strict On prohibits the "=" comparison operator on reference types that do not overload the "=" comparison operator, this includes System.Object! -- Show quoteHide quoteHope this helps Jay B. Harlow ..NET Application Architect, Enthusiast, & Evangelist T.S. Bradley - http://www.tsbradley.net "Göran Andersson" <gu***@guffa.com> wrote in message news:uaLrsst$GHA.3536@TK2MSFTNGP04.phx.gbl... > Jay B. Harlow wrote: >> Göran, >>> which gives that it works the same as comparing identity. >> It sounds like we're quibbling over semantics. ;-) >> >> If it looks like a rose, smells like a rose, tastes like a rose, feels >> like a rose; I would say it must be a rose! >> >> If it "works the same as comparing identity", would that not be the same >> as stating is it identity? It does in my book! ;-) >> > > Yes, it's semantics, that's why it isn't a rose just because it happens to > look like a rose from a certain angle. ;) > > Just because it works like identity doesn't mean that it is identity. > > If you have two integer that have the value two, and multiply them, you > get the result four. If you add them together you also get the result > four. That however does not mean that multiplying and adding is the same > thing in this case. They are still completely different operations > eventhough they give the same result. > > Anyway, the difference between VB.NET and C# isn't really how comparison > works, but what comparison is used. While the C# compiler actually uses > the operator supplied by the Object class to compare Object instances, VB > uses the > Microsoft.VisualBasic.CompilerServices.Operators.CompareObjectEqual method > instead. HI all,
Thank you for your replies, they were helpful. From what I thought was a fairly basic question, the responses did yield some interesting things in VB v C#. Regards, Neville Lang Show quoteHide quote "Neville Lang" <neville@MAPS_ONnjlsoftware.com> wrote in message news:ucODy9$9GHA.3348@TK2MSFTNGP03.phx.gbl... > Hi all, > > I am having a memory blank at the moment. I have been writing in C# for a > number of years and now need to do something in VB.NET, so forgive me such > a primitive question. > > In C#, I test whether a string has a value or not by the following syntax: > > if (thisString.Trim() == "") > { > // if true > something() > } > else > { > // if false > somethingelse() > } > > Now, in VB.NET an equivalent does not seem to work: > > If thisString.Trim() = "" Then > ' if true > something() > Else > ' if false > somethingelse() > End If > > I cannot get past a False return for the VB comparison. What is the best > method for testing whether a string is empty or null? > > > Regards, > Neville Lang > > There is a new declaration type of "Nullable" in vs2005 that I like to
use. For example: Dim ThisString As Nullable(Of String) = Nothing and when you want to check value of ThisString all you have to do is use this syntax: If ThisString.HasValue = True Then 'Do Something End If Neville Lang wrote: Show quoteHide quote > Hi all, > > I am having a memory blank at the moment. I have been writing in C# for a > number of years and now need to do something in VB.NET, so forgive me such a > primitive question. > > In C#, I test whether a string has a value or not by the following syntax: > > if (thisString.Trim() == "") > { > // if true > something() > } > else > { > // if false > somethingelse() > } > > Now, in VB.NET an equivalent does not seem to work: > > If thisString.Trim() = "" Then > ' if true > something() > Else > ' if false > somethingelse() > End If > > I cannot get past a False return for the VB comparison. What is the best > method for testing whether a string is empty or null? > > > Regards, > Neville Lang Jimmy,
> Dim ThisString As Nullable(Of String) = Nothing Of course that causes a compile error as Nullable(Of T) can only be used with types where T is a structure other then Nullable(Of) itself. The rational being that String can already be Nothing; what does ThisString.Value Is Nothing really mean? -- Show quoteHide quoteHope this helps Jay B. Harlow ..NET Application Architect, Enthusiast, & Evangelist T.S. Bradley - http://www.tsbradley.net "JimmyKoolPantz" <kohl.m***@gmail.com> wrote in message news:1161950205.948797.180250@h48g2000cwc.googlegroups.com... > There is a new declaration type of "Nullable" in vs2005 that I like to > use. For example: > > Dim ThisString As Nullable(Of String) = Nothing > > > and when you want to check value of ThisString all you have to do is > use this syntax: > > If ThisString.HasValue = True Then > 'Do Something > End If > > > > > Neville Lang wrote: >> Hi all, >> >> I am having a memory blank at the moment. I have been writing in C# for a >> number of years and now need to do something in VB.NET, so forgive me >> such a >> primitive question. >> >> In C#, I test whether a string has a value or not by the following >> syntax: >> >> if (thisString.Trim() == "") >> { >> // if true >> something() >> } >> else >> { >> // if false >> somethingelse() >> } >> >> Now, in VB.NET an equivalent does not seem to work: >> >> If thisString.Trim() = "" Then >> ' if true >> something() >> Else >> ' if false >> somethingelse() >> End If >> >> I cannot get past a False return for the VB comparison. What is the best >> method for testing whether a string is empty or null? >> >> >> Regards, >> Neville Lang > Jay B. Harlow wrote:
> Jimmy, Actually it's because string is not a value type.>> Dim ThisString As Nullable(Of String) = Nothing > > Of course that causes a compile error as Nullable(Of T) can only be used > with types where T is a structure other then Nullable(Of) itself. > The rational being that String can already be Nothing; what does If the compiler would allow making nullables of objects, the variable > ThisString.Value Is Nothing really mean? having a null value would be perfectly valid. It would be a bit confusing and tedious to use, though, as the variable could have a value and be null at the same time. You would first have to check that it has a value, then check that the value is not null, before you could use the value. >> Of course that causes a compile error as Nullable(Of T) can only be used You do realize we stated the same thing? I stated that Nullable(Of T) >> with types where T is a structure other then Nullable(Of) itself. > > Actually it's because string is not a value type. requires a Value Type (aka a structure), while you confirmed that String is not a value type. -- Show quoteHide quoteHope this helps Jay B. Harlow ..NET Application Architect, Enthusiast, & Evangelist T.S. Bradley - http://www.tsbradley.net "Göran Andersson" <gu***@guffa.com> wrote in message news:%23owFMN6%23GHA.3344@TK2MSFTNGP03.phx.gbl... > Jay B. Harlow wrote: >> Jimmy, >>> Dim ThisString As Nullable(Of String) = Nothing >> >> Of course that causes a compile error as Nullable(Of T) can only be used >> with types where T is a structure other then Nullable(Of) itself. > > Actually it's because string is not a value type. > >> The rational being that String can already be Nothing; what does >> ThisString.Value Is Nothing really mean? > > If the compiler would allow making nullables of objects, the variable > having a null value would be perfectly valid. It would be a bit confusing > and tedious to use, though, as the variable could have a value and be null > at the same time. You would first have to check that it has a value, then > check that the value is not null, before you could use the value.
Outlook PST Files
Looping through files to compare Systray Icon Regular Expressions .NET Issue with VB6 using a .NET DLL on one PC with Windows 2000 Server SQL staments with ADO in Excell Sending CHR(7) to cash drawer to Open Determine what current drive letter is? Collection Question audio functions in Winmm.dll |
|||||||||||||||||||||||