|
code
newsgroups
|
|||||||||||||||||||||||
|
|||||||||||||||||||||||
How to find the datatype of a variable?Can u please tell me to find the datatype of a variable?
for ex: dim a , b as integer here b is an integer datatype. a is in which datatype? Thanks in advance, KarthikeyanP "Karthikeyan Periasamy" <KarthikeyanPerias***@discussions.microsoft.com> You can use the VarType function, but in most cases it returns the "base wrote in message news:0C7240EB-E061-416B-AE13-4E9808C13D2F@microsoft.com... > Can u please tell me to find the datatype of a variable? type" of the variable (such as Long or Integer or whatever) even if it happens to be contained in a Variant (although there are other ways of determing whether it is a Variant or not). > for ex: dim a , b as integer In the above case a is a Variant and b is an Integer. Earlier Basic > here b is an integer datatype. a is in which datatype? languages were in manyh cases different, but in Visual Basic any variable where you do not actually specify the required type will automatically be created as a Variant. So, you need to do: Dim a as Integer, b As Integer In general Variants are to be avoided and you should not normally use them in your code because they are very slow (although there are a few fairly special cases where they are quite useful). To see the speed difference try the following code. Run it as a native code compiled exe: Option Explicit Private Sub Command1_Click() Dim a, b As Long a = 1&: b = 1& Me.Print "a is type " & VarType(a) Me.Print "b is type " & VarType(a) Me.Print "Please wait . . ." Me.Print DoEvents Dim t1 As Single, t2 As Single, n As Long t1 = Timer For n = 1 To 100000000 a = a + 1 Next n t2 = Timer Print t2 - t1 & " seconds for a" t1 = Timer For n = 1 To 100000000 b = b + 1 Next n t2 = Timer Print t2 - t1 & " seconds for b" End Sub Mike Your example code brings up an tangentially-related question: does it make a difference whether you do "a = 1", "a = 1&", or "a =
CLng(1)"? Wouldn't they all produce more or less the same code in the end? The first one would have implicit conversion rather than explicit, but would it really make a difference? (PS, before anybody says to try this, which I know would be ridiculously simple, consider the fact that this time yesterday, my computer was in bits & pieces as I installed a new motherboard, and a few hours later saw a slip-streamed version of XPSP2 + Updates being loaded. VB6 hasn't yet made it's way into the new installation. I don't even have all my critical, use-'em-every-day apps in yet...though I'm not far from finishing that, at least.) Rob Show quote "Mike Williams" <mi***@whiskyandCoke.com> wrote in message news:uCtAo61LIHA.4808@TK2MSFTNGP05.phx.gbl... > You can use the VarType function, but in most cases it returns the "base type" of the variable (such as Long or Integer or > whatever) even if it happens to be contained in a Variant (although there are other ways of determing whether it is a Variant or > not). > > In the above case a is a Variant and b is an Integer. Earlier Basic languages were in manyh cases different, but in Visual Basic > any variable where you do not actually specify the required type will automatically be created as a Variant. So, you need to do: > > Dim a as Integer, b As Integer > > In general Variants are to be avoided and you should not normally use them in your code because they are very slow (although there > are a few fairly special cases where they are quite useful). To see the speed difference try the following code. Run it as a > native code compiled exe: > > Option Explicit > > Private Sub Command1_Click() > Dim a, b As Long > a = 1&: b = 1& > Me.Print "a is type " & VarType(a) > Me.Print "b is type " & VarType(a) > Me.Print "Please wait . . ." > Me.Print > DoEvents > Dim t1 As Single, t2 As Single, n As Long > t1 = Timer > For n = 1 To 100000000 > a = a + 1 > Next n > t2 = Timer > Print t2 - t1 & " seconds for a" > t1 = Timer > For n = 1 To 100000000 > b = b + 1 > Next n > t2 = Timer > Print t2 - t1 & " seconds for b" > End Sub > > Mike "Robert Morley" <rmor***@magma.ca.N0.Freak1n.sparn> wrote in message Pardon? Tangentially-related question? Did you eat a dictionary for news:OGT%23Wt5LIHA.6108@TK2MSFTNGP03.phx.gbl... > Your example code brings up an tangentially-related question: breakfast? We all know (or can figure out) what the phrase "tangentially-related question" means, but do they really talk like that in your neck of the woods? I must admit that I've had a few glasses of Californian 13.5% (by vol) Chardonnay tonight (a really nice buttery yet flavoursome wine that was reduced from £7.99 to £3.99 with an additional 33.3% reduction if you buy six bottles at a time, bringing it to a very nice £2.66 per bottle) but even after half a bottle of that stuff I can still just about get my brain around the word "tangentially" ;-) > does it make a difference whether you do "a = 1", Yes.> "a = 1&", or "a = CLng(1)"? > Wouldn't they all produce more or less the same No.> result in the end? > The first one would have implicit conversion rather than explicit, but Yes.> would it really make a difference? Try the following (on a Form with two Command Buttons): Private Sub Command1_Click() Dim a, b As Long a = 1: b = 1 MsgBox VarType(a) & vbTab & VarType(b) End Sub Private Sub Command2_Click() Dim a, b As Long a = 1&: b = 1& MsgBox VarType(a) & vbTab & VarType(b) End Sub Can you see the difference? Mike > Pardon? Tangentially-related question? Did you eat a dictionary for breakfast? Sorry, I'm a geek, and if I hadn't gone into computers, I probably would've gone into linguistics or mathematics.> Try the following (on a Form with two Command Buttons): As soon as I get VB loaded once again, I'll do that. :-)Oh, and that was my bad in my original example; I should've used "b" instead of "a". It was the conversion to long with a variable already declared as long that I was interested in, not the variant. Rob "Robert Morley" <rmor***@magma.ca.N0.Freak1n.sparn> wrote in message Now this is where I'm really confused. You throw phrases like "tangentially news:eoWrNf6LIHA.4880@TK2MSFTNGP03.phx.gbl... >> Pardon? Tangentially-related question? Did you eat a dictionary for >> breakfast? > > Sorry, I'm a geek [Tangentially-related question], and if > I hadn't gone into computers, I probably would've gone > into linguistics or mathematics. Oh, and that was my bad in my original > example; I should've > used "b" instead of "a". related question" about as though you use them every day and yet you also use "pidgin English" phrases such as, "and that was my bad", which is definitely not a valid English phrase or sentence because it does not contain the required parts. It's almost as though you are two different people. As far as I can see you live somewhere near Ottawa in Canada, which I assume is an English speaking area, even though the people there do probably also use French. What is going on? Also, I've seen the phrase "was my bad" used in other posts by at least one other person on this group, and I wonder what you intend it to mean? Would you care to elucidate? Mike First, yes, you see correctly. I'm in Ottawa and the main language here is English, but with lots of French as well...probably more
French than in other Ontario cities, since this is the nation's capital and we have a large number of government offices here which must serve the public in both languages. "My bad" has become a common way of saying "my mistake" or "my fault", but with a bit more of a sheepish or light-hearted quality to it. Using "bad" in this context is distinctly grammatically incorrect, at least in traditional usage, but it's become common enough, and I find it amusing enough, that I've picked it up. Call it "evolution in action"...or if you prefer, "devolution in action". <g> I guess that's a North American colloquialism or something and hasn't made its way to the UK yet, where you appear to be. (And it IS clearly a colloquialism; nobody would ever use that term in formal writing.) Oh and yes, "tangentially-related (question/topic/whatever)" IS a common phrase for me; this is the first time anybody's mentioned that it might not be for everyone. Finally, if you're uncomfortable with "tangentially", how can you turn around and use "elucidate"? :-) I dunno about anybody else, but I'd consider "elucidate" to be a linguistic step more complex than "tangentially". Rob Show quote "Mike Williams" <mi***@whiskyandCoke.com> wrote in message news:ehsnHi7LIHA.3400@TK2MSFTNGP03.phx.gbl... > Now this is where I'm really confused. You throw phrases like "tangentially related question" about as though you use them every > day and yet you also use "pidgin English" phrases such as, "and that was my bad", which is definitely not a valid English phrase > or sentence because it does not contain the required parts. It's almost as though you are two different people. As far as I can > see you live somewhere near Ottawa in Canada, which I assume is an English speaking area, even though the people there do probably > also use French. What is going on? Also, I've seen the phrase "was my bad" used in other posts by at least one other person on > this group, and I wonder what you intend it to mean? Would you care to elucidate? > > Mike
Show quote
"Robert Morley" <rmor***@magma.ca.N0.Freak1n.sparn> wrote in message Shakespeare used the phrase with something like the current meaning in his news:OJmIs77LIHA.2268@TK2MSFTNGP02.phx.gbl... > First, yes, you see correctly. I'm in Ottawa and the main language here > is English, but with lots of French as well...probably more French than in > other Ontario cities, since this is the nation's capital and we have a > large number of government offices here which must serve the public in > both languages. > > "My bad" has become a common way of saying "my mistake" or "my fault", but > with a bit more of a sheepish or light-hearted quality to it. Using "bad" > in this context is distinctly grammatically incorrect, at least in > traditional usage, but it's become common enough, and I find it amusing > enough, that I've picked it up. Call it "evolution in action"...or if you > prefer, "devolution in action". <g> > > I guess that's a North American colloquialism or something and hasn't made > its way to the UK yet, where you appear to be. (And it IS clearly a > colloquialism; nobody would ever use that term in formal writing.) Sonnet 112. It became famous in the US when it was used in the movie Clueless in the mid-nineties. It came into use in NBA basketball by Manute Bol. Manute Bol was the tallest player in professional basketball. Instead of saying "my fault" when he made a bad pass, he said "my bad". The other players picked it up. The fans followed suit so it is apparently common in street basketball. Show quote > > Oh and yes, "tangentially-related (question/topic/whatever)" IS a common > phrase for me; this is the first time anybody's mentioned that it might > not be for everyone. > > Finally, if you're uncomfortable with "tangentially", how can you turn > around and use "elucidate"? :-) I dunno about anybody else, but I'd > consider "elucidate" to be a linguistic step more complex than > "tangentially". > > > Rob > > "Mike Williams" <mi***@whiskyandCoke.com> wrote in message > news:ehsnHi7LIHA.3400@TK2MSFTNGP03.phx.gbl... >> Now this is where I'm really confused. You throw phrases like >> "tangentially related question" about as though you use them every day >> and yet you also use "pidgin English" phrases such as, "and that was my >> bad", which is definitely not a valid English phrase or sentence because >> it does not contain the required parts. It's almost as though you are two >> different people. As far as I can see you live somewhere near Ottawa in >> Canada, which I assume is an English speaking area, even though the >> people there do probably also use French. What is going on? Also, I've >> seen the phrase "was my bad" used in other posts by at least one other >> person on this group, and I wonder what you intend it to mean? Would you >> care to elucidate? >> >> Mike > rialto wrote:
.... > It came into use in NBA basketball by Manute Bol. ... The phrase was around long before Bol was...although he was longer... :)Manute had a niece who played here for the local community college. She was "only" 6'-8" and was a sweetheart...she went on to Louisiana Tech but I've lost track of her ofter that... -- I see I'm not the only one with linguistic interests in this group. Do you have an etymology degree, rialto? <g>
Rob Show quote "rialto" <noname@nospam.com> wrote in message news:uNg3wO8LIHA.4688@TK2MSFTNGP06.phx.gbl... > Shakespeare used the phrase with something like the current meaning in his > Sonnet 112. > > It became famous in the US when it was used in the movie Clueless in the > mid-nineties. > > It came into use in NBA basketball by Manute Bol. Manute Bol was the > tallest player in professional basketball. Instead of saying "my fault" when > he made a bad pass, he said "my bad". The other players picked it up. The > fans followed suit so it is apparently common in street basketball. "Robert Morley" <rmor***@magma.ca.N0.Freak1n.sparn> wrote in message I had to look up etymology so the answer is no. It's ironic that we find news:uRZg1N%23LIHA.748@TK2MSFTNGP04.phx.gbl... >I see I'm not the only one with linguistic interests in this group. Do you >have an etymology degree, rialto? <g> > > > Rob > ourselves at the stage in the process where we can track this phrase transferring from one language to another: North American English to English. :-) Show quote > "rialto" <noname@nospam.com> wrote in message > news:uNg3wO8LIHA.4688@TK2MSFTNGP06.phx.gbl... >> Shakespeare used the phrase with something like the current meaning in >> his Sonnet 112. >> >> It became famous in the US when it was used in the movie Clueless in the >> mid-nineties. >> >> It came into use in NBA basketball by Manute Bol. Manute Bol was the >> tallest player in professional basketball. Instead of saying "my fault" >> when he made a bad pass, he said "my bad". The other players picked it >> up. The fans followed suit so it is apparently common in street >> basketball. "Robert Morley" <rmor***@magma.ca.N0.Freak1n.sparn> wrote in message Very good point :-) But as you will of course realise, I was just kiddin' news:OJmIs77LIHA.2268@TK2MSFTNGP02.phx.gbl... > Finally, if you're uncomfortable with "tangentially", how > can you turn around and use "elucidate"? :-) I dunno > about anybody else, but I'd consider "elucidate" to be > a linguistic step more complex than "tangentially". ya ;-) Mike "Mike Williams" <mi***@whiskyandCoke.com> wrote in message I do....news:%23RH2oR6LIHA.4196@TK2MSFTNGP04.phx.gbl... > "Robert Morley" <rmor***@magma.ca.N0.Freak1n.sparn> wrote in message > news:OGT%23Wt5LIHA.6108@TK2MSFTNGP03.phx.gbl... > >> Your example code brings up an tangentially-related question: > > Pardon? Tangentially-related question? Did you eat a dictionary for > breakfast? We all know (or can figure out) what the phrase > "tangentially-related question" means, but do they really talk like that > in your neck of the woods? "Mike Williams" <mi***@whiskyandCoke.com> wrote in message Round here we say "a" tangentially-related question, reserving the use of "an" news:%23RH2oR6LIHA.4196@TK2MSFTNGP04.phx.gbl... > "Robert Morley" <rmor***@magma.ca.N0.Freak1n.sparn> wrote in message > news:OGT%23Wt5LIHA.6108@TK2MSFTNGP03.phx.gbl... > >> Your example code brings up an tangentially-related question: > > Pardon? Tangentially-related question? Did you eat a dictionary for breakfast? > We all know (or can figure out) what the phrase "tangentially-related > question" means, but do they really talk like that in your neck of the woods? for words beginning with a vowel. :) Speaking of really talking like that, do you really say "your neck of the woods" in your neck of the woods? :) "Steve Gerrard" <mynameh***@comcast.net> wrote in message I say that too!news:E-GdnbWvdq-4a9TanZ2dnUVZ_rmjnZ2d@comcast.com... > Speaking of really talking like that, do you really say "your neck of the > woods" in your neck of the woods? :) <g> "Steve Gerrard" <mynameh***@comcast.net> wrote in message We do *almost* the same here in England, reserving "an" for words beginning news:E-GdnbWvdq-4a9TanZ2dnUVZ_rmjnZ2d@comcast.com... > Round here we say "a" tangentially-related question, reserving > the use of "an" for words beginning with a vowel. :) with a vowel and otherwise using "a", except that there are certain exceptions to that rule. For example, many words beginning with "h" are also preceded by the word "an", for example "an hotel", where in fact the "h" is silent, so it is correctly pronounced "an otel". Mike "Steve Gerrard" <mynameh***@comcast.net> wrote in message Well, we do in this neck of the woods, but I think the phrase really began news:E-GdnbWvdq-4a9TanZ2dnUVZ_rmjnZ2d@comcast.com... > Speaking of really talking like that, do you really say > "your neck of the woods" in your neck of the woods? :) in "hill billy" America ;-) Mike > Round here we say "a" tangentially-related question, reserving the use of "an" for words beginning with a vowel. :) Yeah, I noticed that after I sent it. I don't remember what I'd had in there initially, but I did some editing and didn't notice the extra "n" left over. > Speaking of really talking like that, do you really say "your neck of the woods" in your neck of the woods? :) Speaking for myself, I generally wouldn't, but others would. I know my mother does sometimes. At the risk of sounding classist, my impression is that it's more of an informal, blue-collar sort of phrase. Rob Robert Morley wrote:
>> Round here we say "a" tangentially-related question, reserving the use How dare you try to make it that up-scale! :)>> of "an" for words beginning with a vowel. :) > > Yeah, I noticed that after I sent it. I don't remember what I'd had in > there initially, but I did some editing and didn't notice the extra "n" > left over. > >> Speaking of really talking like that, do you really say "your neck of >> the woods" in your neck of the woods? :) > > Speaking for myself, I generally wouldn't, but others would. I know my > mother does sometimes. At the risk of sounding classist, my impression > is that it's more of an informal, blue-collar sort of phrase. It's common here, where there's not a native tree within 200 miles... -- "Robert Morley" <rmor***@magma.ca.N0.Freak1n.sparn> wrote in message of "an" for words beginning with a vowel. :)news:O6Rcs77LIHA.2268@TK2MSFTNGP02.phx.gbl... > > Round here we say "a" tangentially-related question, reserving the use > there initially, but I did some editing and didn't notice> Yeah, I noticed that after I sent it. I don't remember what I'd had in > the extra "n" left over. the woods" in your neck of the woods? :)> > > Speaking of really talking like that, do you really say "your neck of > mother does sometimes. At the risk of sounding classist, my> Speaking for myself, I generally wouldn't, but others would. I know my > impression is that it's more of an informal, blue-collar sort of phrase. As an idiom it would always be considered informal or slang, but it comes> from our early history, our pioneers - whom were farmers, teachers, lawyers, doctors, industrialists, merchants, and tramps 'n thieves. It would be elitist and less than honorable to call them "blue-collar". <g> -ralph "Robert Morley" <rmor***@magma.ca.N0.Freak1n.sparn> wrote in message Besides the Variant-explict data type examples the Mike provided (which I news:OGT%23Wt5LIHA.6108@TK2MSFTNGP03.phx.gbl... > Your example code brings up an tangentially-related question: does it > make a difference whether you do "a = 1", "a = 1&", or "a = CLng(1)"? > Wouldn't they all produce more or less the same code in the end? The > first one would have implicit conversion rather than explicit, but would > it really make a difference? > don't think were quite hitting at what you were getting at, but maybe), there CAN be a difference even when the declared data type is identical. Consider this: Dim A As Long Dim B As Long A = &HFFFF B = &HFFFF& Debug.Print A, B The output of this is: -1 65535 In this case, that trailing ampersand to force the numeric to be a Long is critical. But I believe this is a hex-only thing. I don't think you'd ever run into this with decimal values. Anyway, because of this, whenever I use hex values, I ALWAYS include the trailing ampersand to force a Long. If it's not needed, VB will automatically remove it. -- Mike Microsoft MVP Visual Basic Yes, I realized my mistake and "fixed it" in a later message...you've correctly understood what I was actually getting at.
I'm aware of the type conversion (-1 vs. 65535) issue you mentioned, so I guess that would point to SOME difference in how the conversion is done. I'm just wondering why you would do something like type "1&" instead of simply "1", though, where you know the conversion will occur correctly. I'm just in the process of installing VB6 and the Oct 2001 MSDN Subscription Library now, so I guess I'll be able to test timing and so forth soon. :) Rob Show quote "MikeD" <nob***@nowhere.edu> wrote in message news:ucl$BS7LIHA.2268@TK2MSFTNGP02.phx.gbl... > > "Robert Morley" <rmor***@magma.ca.N0.Freak1n.sparn> wrote in message news:OGT%23Wt5LIHA.6108@TK2MSFTNGP03.phx.gbl... >> Your example code brings up an tangentially-related question: does it make a difference whether you do "a = 1", "a = 1&", or "a >> = CLng(1)"? Wouldn't they all produce more or less the same code in the end? The first one would have implicit conversion rather >> than explicit, but would it really make a difference? >> > > Besides the Variant-explict data type examples the Mike provided (which I don't think were quite hitting at what you were getting > at, but maybe), there CAN be a difference even when the declared data type is identical. Consider this: > > Dim A As Long > Dim B As Long > > A = &HFFFF > B = &HFFFF& > > Debug.Print A, B > > The output of this is: > > -1 65535 > > In this case, that trailing ampersand to force the numeric to be a Long is critical. But I believe this is a hex-only thing. I > don't think you'd ever run into this with decimal values. Anyway, because of this, whenever I use hex values, I ALWAYS include the > trailing ampersand to force a Long. If it's not needed, VB will automatically remove it. > > -- > Mike > Microsoft MVP Visual Basic > > Debug.Print VarType(1), VarType(1&)
produces 2 3 meaning integer long So I think VB takes 1 as an integer, unless something in the expression "upgrades" it to a long or a double. However, I suspect that the compiler can recognize the upgrade in most cases, and code the 1 as a long constant at compile time, rather than as an integer with accompanying conversion code, so I doubt it would affect performance very often. Show quote "Robert Morley" <rmor***@magma.ca.N0.Freak1n.sparn> wrote in message news:urBA399LIHA.2140@TK2MSFTNGP03.phx.gbl... > Yes, I realized my mistake and "fixed it" in a later message...you've > correctly understood what I was actually getting at. > > I'm aware of the type conversion (-1 vs. 65535) issue you mentioned, so I > guess that would point to SOME difference in how the conversion is done. I'm > just wondering why you would do something like type "1&" instead of simply > "1", though, where you know the conversion will occur correctly. > > I'm just in the process of installing VB6 and the Oct 2001 MSDN Subscription > Library now, so I guess I'll be able to test timing and so forth soon. :) > > > > Rob > > "MikeD" <nob***@nowhere.edu> wrote in message > news:ucl$BS7LIHA.2268@TK2MSFTNGP02.phx.gbl... >> >> "Robert Morley" <rmor***@magma.ca.N0.Freak1n.sparn> wrote in message >> news:OGT%23Wt5LIHA.6108@TK2MSFTNGP03.phx.gbl... >>> Your example code brings up an tangentially-related question: does it make >>> a difference whether you do "a = 1", "a = 1&", or "a = CLng(1)"? Wouldn't >>> they all produce more or less the same code in the end? The first one would >>> have implicit conversion rather than explicit, but would it really make a >>> difference? >>> >> >> Besides the Variant-explict data type examples the Mike provided (which I >> don't think were quite hitting at what you were getting at, but maybe), there >> CAN be a difference even when the declared data type is identical. Consider >> this: >> >> Dim A As Long >> Dim B As Long >> >> A = &HFFFF >> B = &HFFFF& >> >> Debug.Print A, B >> >> The output of this is: >> >> -1 65535 >> >> In this case, that trailing ampersand to force the numeric to be a Long is >> critical. But I believe this is a hex-only thing. I don't think you'd ever >> run into this with decimal values. Anyway, because of this, whenever I use >> hex values, I ALWAYS include the trailing ampersand to force a Long. If it's >> not needed, VB will automatically remove it. >> >> -- >> Mike >> Microsoft MVP Visual Basic >> >> > That was my thought as well. I'll try some tests tomorrow and see what happens, but the last time I compared the performance of
integers vs. longs in VB, the difference was only a couple of percent, so I don't know if there will be anything noticeable. Of course, at that level of non-difference, it's probably about the last thing you should waste time worrying about, but just for the hell of it, I'll give it a shot and see if there's anything noticeable. Rob Show quote "Steve Gerrard" <mynameh***@comcast.net> wrote in message news:PIKdnYAgP5gZztfanZ2dnUVZ_j-dnZ2d@comcast.com... > Debug.Print VarType(1), VarType(1&) > produces > 2 3 > meaning > integer long > > So I think VB takes 1 as an integer, unless something in the expression "upgrades" it to a long or a double. > > However, I suspect that the compiler can recognize the upgrade in most cases, and code the 1 as a long constant at compile time, > rather than as an integer with accompanying conversion code, so I doubt it would affect performance very often. > > > "Robert Morley" <rmor***@magma.ca.N0.Freak1n.sparn> wrote in message news:urBA399LIHA.2140@TK2MSFTNGP03.phx.gbl... >> Yes, I realized my mistake and "fixed it" in a later message...you've correctly understood what I was actually getting at. >> >> I'm aware of the type conversion (-1 vs. 65535) issue you mentioned, so I guess that would point to SOME difference in how the >> conversion is done. I'm just wondering why you would do something like type "1&" instead of simply "1", though, where you know >> the conversion will occur correctly. >> >> I'm just in the process of installing VB6 and the Oct 2001 MSDN Subscription Library now, so I guess I'll be able to test timing >> and so forth soon. :) >> >> >> >> Rob >> >> "MikeD" <nob***@nowhere.edu> wrote in message news:ucl$BS7LIHA.2268@TK2MSFTNGP02.phx.gbl... >>> >>> "Robert Morley" <rmor***@magma.ca.N0.Freak1n.sparn> wrote in message news:OGT%23Wt5LIHA.6108@TK2MSFTNGP03.phx.gbl... >>>> Your example code brings up an tangentially-related question: does it make a difference whether you do "a = 1", "a = 1&", or >>>> "a = CLng(1)"? Wouldn't they all produce more or less the same code in the end? The first one would have implicit conversion >>>> rather than explicit, but would it really make a difference? >>>> >>> >>> Besides the Variant-explict data type examples the Mike provided (which I don't think were quite hitting at what you were >>> getting at, but maybe), there CAN be a difference even when the declared data type is identical. Consider this: >>> >>> Dim A As Long >>> Dim B As Long >>> >>> A = &HFFFF >>> B = &HFFFF& >>> >>> Debug.Print A, B >>> >>> The output of this is: >>> >>> -1 65535 >>> >>> In this case, that trailing ampersand to force the numeric to be a Long is critical. But I believe this is a hex-only thing. I >>> don't think you'd ever run into this with decimal values. Anyway, because of this, whenever I use hex values, I ALWAYS include >>> the trailing ampersand to force a Long. If it's not needed, VB will automatically remove it. >>> >>> -- >>> Mike >>> Microsoft MVP Visual Basic >>> >>> >> > > > "Robert Morley" <rmor***@magma.ca.N0.Freak1n.sparn> wrote in message I did that specifically to illustrate the point I was making when the OP news:urBA399LIHA.2140@TK2MSFTNGP03.phx.gbl... > I'm just wondering why you would do something like > type "1&" instead of simply "1", though, where you > know the conversion will occur correctly. asked what kind of variables he would get when he declared them in the manner Dim a, b as Long, so I did this . . . Dim a, b As Long a = 1: b = 1 Print VarType(a), VarType(b) .. . . which clearly illustrates that a is definitely not a Long (which the OP though it might be and which would actually be the case in other early versions of Basic) and that it is actually a Variant, in this case containing a variable of the type Integer (not Long). I then followed that with: Dim a, b As Long a = 1&: b = 1& Print VarType(a), VarType(b) .. . . to make it even clearer. But perhaps I just muddied the waters :-( Mike Well, I just tested it using a fairly primitive test, and got some not-too-surprising results.
In the IDE, the test below took MUCH longer, and came out with roughly the same results in each variation of the test; in a compiled EXE with all optimizations turned on and "Favor Pentium Pro" enabled (if that makes any difference at this point), the first test came out noticeably slower than the others, though (2.5 s on average vs. 2.0 s for the other two). This was done on a Core2 Duo @ 3.0 GHz. The results would seem to confirm that the simple "a = 1" assignment is implicitly converting to an integer, then up to a long. When I changed it to "a = 65536", the results of all three tests were identical. Anyway, here's the code I used to test...the dummy assignment is required to ensure the various "a=1" assignments don't get optimized out of existence. Private mlngDummy As Long Private Sub Command1_Click() Const clngReps As Long = 1000000000 Dim a As Long Dim i As Long ' Text1.MultiLine = True Text1.Text = vbNullString t = Timer() For i = 1 To clngReps a = 1 mlngDummy = mlngDummy + a Next Text1.Text = Text1.Text & Format(Timer - t, "0.000") & vbCrLf DoEvents t = Timer() For i = 1 To clngReps a = 1& mlngDummy = mlngDummy + a Next Text1.Text = Text1.Text & Format(Timer - t, "0.000") & vbCrLf DoEvents t = Timer() For i = 1 To clngReps a = CLng(1) mlngDummy = mlngDummy + a Next Text1.Text = Text1.Text & Format(Timer - t, "0.000") & vbCrLf Text1.Text = Text1.Text & mlngDummy & " iterations" End Sub
Show quote
"Robert Morley" <rmor***@magma.ca.N0.Freak1n.sparn> wrote in message Well, I got some interesting results with your code. :)news:%23InsAzHMIHA.4272@TK2MSFTNGP05.phx.gbl... > Well, I just tested it using a fairly primitive test, and got some > not-too-surprising results. > > In the IDE, the test below took MUCH longer, and came out with roughly the > same results in each variation of the test; in a compiled EXE with all > optimizations turned on and "Favor Pentium Pro" enabled (if that makes any > difference at this point), the first test came out noticeably slower than the > others, though (2.5 s on average vs. 2.0 s for the other two). This was done > on a Core2 Duo @ 3.0 GHz. > > The results would seem to confirm that the simple "a = 1" assignment is > implicitly converting to an integer, then up to a long. When I changed it to > "a = 65536", the results of all three tests were identical. > First, I had to add mlngDummy = 0 before each loop, because it was unhappy being run up to 3 billion. Second, I got this (or similar in range of 2.5 to 2.6), with only standard fast code optimization: 2.578 2.578 2.656 Third, the Favor Pentium Pro option slowed it down to a 3 - 3.6 range. I believe the docs state that this option produces code that is slower when run on non Pentium Pro chips. Fourth, using 65536 (and avoiding overflow by just adding 1 to mlngDummy) made no significant difference. Fifth (and this is the good one), the optimization "Remove Integer Overflow Checks" slowed it down quite a bit: 5.297 5.375 5.250 In conclusion, on my machine (P4, 2.4 GHz), 1 or 1& or CLng(1) give essentially the same result, and the "optimization" of "Remove Integer Overflow Checks" is not an optimization at all in some cases. I would love to know if that last one is reproducible by others. I'd noticed the mlngDummy issue (even more obvious when running Command1_Click multiple times), but didn't worry about it because I
figured it was irrelevant to the code with the overflow checks turned off...little did I know! So I added your mlngDummy = 0, changed the optimizations to test your observations about the integer overflow checks, and ran the code. You're absolutely right, leaving the overflow checks ON, the code runs significantly faster than removing them (WTF?!?). Unlike earlier, though, all times came out the same (give or take), regardless of which optimizations I set. Naturally, the letters W, T, and F were still foremost in my mind. Well, after a few more minutes of playing, it finally occurred to me to comment out the newly-inserted mlngDummy = 0 line. Sure enough, the first iteration got MUCH longer! Interestingly, this was only the case when remove integer overflow checking was checked; unchecked, this didn't happen. The letters W, T, and F are now in huge, bold, all-caps lettering in my mind. VB never ceases to surprise me. Rob Show quote "Steve Gerrard" <mynameh***@comcast.net> wrote in message news:DqidnQZFKPTFBtbanZ2dnUVZ_hynnZ2d@comcast.com... > Well, I got some interesting results with your code. :) > > First, I had to add > mlngDummy = 0 > before each loop, because it was unhappy being run up to 3 billion. > > Second, I got this (or similar in range of 2.5 to 2.6), with only standard fast code optimization: > 2.578 > 2.578 > 2.656 > > Third, the Favor Pentium Pro option slowed it down to a 3 - 3.6 range. I believe the docs state that this option produces code > that is slower when run on non Pentium Pro chips. > > Fourth, using 65536 (and avoiding overflow by just adding 1 to mlngDummy) made no significant difference. > > Fifth (and this is the good one), the optimization "Remove Integer Overflow Checks" slowed it down quite a bit: > 5.297 > 5.375 > 5.250 > > In conclusion, on my machine (P4, 2.4 GHz), 1 or 1& or CLng(1) give essentially the same result, and the "optimization" of "Remove > Integer Overflow Checks" is not an optimization at all in some cases. I would love to know if that last one is reproducible by > others. I tried it again, without the mlngDummy = 0, and with "remove integer overflow
checks" checked. I get a longer time for all three loops, but again all about the same. WTF squared. Show quote "Robert Morley" <rmor***@magma.ca.N0.Freak1n.sparn> wrote in message news:%23W8S8XLMIHA.4684@TK2MSFTNGP06.phx.gbl... > I'd noticed the mlngDummy issue (even more obvious when running Command1_Click > multiple times), but didn't worry about it because I figured it was irrelevant > to the code with the overflow checks turned off...little did I know! > > So I added your mlngDummy = 0, changed the optimizations to test your > observations about the integer overflow checks, and ran the code. You're > absolutely right, leaving the overflow checks ON, the code runs significantly > faster than removing them (WTF?!?). Unlike earlier, though, all times came out > the same (give or take), regardless of which optimizations I set. Naturally, > the letters W, T, and F were still foremost in my mind. > > Well, after a few more minutes of playing, it finally occurred to me to > comment out the newly-inserted mlngDummy = 0 line. Sure enough, the first > iteration got MUCH longer! Interestingly, this was only the case when remove > integer overflow checking was checked; unchecked, this didn't happen. The > letters W, T, and F are now in huge, bold, all-caps lettering in my mind. VB > never ceases to surprise me. > > VB simply can't optimize the single method. If you bust out each
for..next loop into 3 different subs, you'll see significantly different results. Here is how I rewrote the original test: Private mlngDummy As Long Const clngReps As Long = 1000000000 Private Sub Command1_Click() Dim a As Long Dim i As Long Dim t As Single ' Text1.MultiLine = True Text1.Text = vbNullString mlngDummy = &H80000000 ' keeps from overflowing. t = Timer() RepsWithInt Text1.Text = Text1.Text & Format(Timer - t, "0.000") & vbCrLf DoEvents t = Timer() RepsWithLong Text1.Text = Text1.Text & Format(Timer - t, "0.000") & vbCrLf DoEvents t = Timer() RepsWithCLng Text1.Text = Text1.Text & Format(Timer - t, "0.000") & vbCrLf Text1.Text = Text1.Text & mlngDummy & " iterations" End Sub Private Sub RepsWithInt() Dim i As Long Dim a As Long For i = 1 To clngReps a = 1 mlngDummy = mlngDummy + a Next End Sub Private Sub RepsWithLong() Dim i As Long Dim a As Long For i = 1 To clngReps a = 1& mlngDummy = mlngDummy + a Next End Sub Private Sub RepsWithCLng() Dim i As Long Dim a As Long For i = 1 To clngReps a = CLng(1) mlngDummy = mlngDummy + a Next End Sub Steve Gerrard wrote: Show quote > I tried it again, without the mlngDummy = 0, and with "remove integer overflow > checks" checked. I get a longer time for all three loops, but again all about > the same. WTF squared. > > > "Robert Morley" <rmor***@magma.ca.N0.Freak1n.sparn> wrote in message > news:%23W8S8XLMIHA.4684@TK2MSFTNGP06.phx.gbl... >> I'd noticed the mlngDummy issue (even more obvious when running Command1_Click >> multiple times), but didn't worry about it because I figured it was irrelevant >> to the code with the overflow checks turned off...little did I know! >> >> So I added your mlngDummy = 0, changed the optimizations to test your >> observations about the integer overflow checks, and ran the code. You're >> absolutely right, leaving the overflow checks ON, the code runs significantly >> faster than removing them (WTF?!?). Unlike earlier, though, all times came out >> the same (give or take), regardless of which optimizations I set. Naturally, >> the letters W, T, and F were still foremost in my mind. >> >> Well, after a few more minutes of playing, it finally occurred to me to >> comment out the newly-inserted mlngDummy = 0 line. Sure enough, the first >> iteration got MUCH longer! Interestingly, this was only the case when remove >> integer overflow checking was checked; unchecked, this didn't happen. The >> letters W, T, and F are now in huge, bold, all-caps lettering in my mind. VB >> never ceases to surprise me. >> >> > > "Kelly Ethridge" <ke***@kellyethridge.com> wrote in message I got better times, using the 3 seperate subs you posted, with both regular and news:%236k2PiNMIHA.2268@TK2MSFTNGP02.phx.gbl... > VB simply can't optimize the single method. If you bust out each for..next > loop into 3 different subs, you'll see significantly different results. > > Here is how I rewrote the original test: > (snipped) deluxe optimization. All three came out about the same in both cases. Deluxe optimization was quite a bit faster than regular. So the separate subs helps the optimizer work. Awkward, though, that with a more elaborate single sub, the optimization is actually worse. The lesson here is that function/sub overhead is a good price to pay, since it lets the optimizer do a better job. Like everyone else, I got much better times (by a factor of about 3) when doing it as separate routines, and the expected change in
times when removing integer overflow checks instead of the reverse. Interestingly, moving "a" to a module variable and removing it from each individual sub made the execution times for the three separate routines a bit slower, and the three portions of the same routine faster, but they showed more significant differences between them. I think all this goes to show just how amusingly-designed VB's optimizations really are, especially given that they were largely written for VC originally. If your program is running slowly, try just randomly moving variables around or initializing a variable or two (or initializing them in different places). It might make your code significantly faster! To quote Deanna Troy, "In another time and place, this could be funny." Rob Show quote "Steve Gerrard" <mynameh***@comcast.net> wrote in message news:e8idnSIq7uvS3NHanZ2dnUVZ_sOrnZ2d@comcast.com... > I got better times, using the 3 seperate subs you posted, with both regular and deluxe optimization. > > All three came out about the same in both cases. Deluxe optimization was quite a bit faster than regular. > > So the separate subs helps the optimizer work. Awkward, though, that with a more elaborate single sub, the optimization is > actually worse. > > The lesson here is that function/sub overhead is a good price to pay, since it lets the optimizer do a better job. "Robert Morley" <rmor***@magma.ca.N0.Freak1n.sparn> wrote in message doing it as separate routines, and the expected change innews:OpvkIsRMIHA.4912@TK2MSFTNGP06.phx.gbl... > Like everyone else, I got much better times (by a factor of about 3) when > times when removing integer overflow checks instead of the reverse. individual sub made the execution times for the three> > Interestingly, moving "a" to a module variable and removing it from each > separate routines a bit slower, and the three portions of the same routine faster, but they showed more significant differences> between them. optimizations really are, especially given that they were largely> > I think all this goes to show just how amusingly-designed VB's > written for VC originally. If your program is running slowly, try just randomly moving variables around or initializing a variable> or two (or initializing them in different places). It might make your code significantly faster!> <snipped>> To quote Deanna Troy, "In another time and place, this could be funny." > > > Rob > There is little mystery surrounding the optimization settings. Remember that they are only a 'request' to the compiler to run (or avoid) certain optimizers. If the compiler can't comply nothing happens. Most of the time one can easily determine what may improve or what may decrease performance. For example, moving the 'a' variable to the module level removed it from the realm of automatic variables to a default data segment, thus external to the routine. You will find most optimizations work best with local variables that the compiler can play with. (Like putting them in a register.) Something along the same line happens when you place multiple loops, reusing the same variables, within a single routine. While not that germane here - you might take a look at "aliasing" sometime. Which often because of VB's love of references often precludes various optimizations. -ralph Yeah, I wasn't really surprised by the fact that moving the variable up a level made it slower. I certainly *was* surprised when
removing integer overflow checks made the program run slower...don't tell me there's "no mystery" there! :-) I don't understand why multiple loops in the same routine would have posed a problem, though. You should still be able to use the same code, regardless whether it was one loop per routine or three in the same one...but I suppose compilers can't always understand how we intend for them to interpret things. As for aliasing, I remember looking up why aliasing was a problem some time ago, though I don't remember the specifics now. All I needed to know was that I pretty much never use it, and shouldn't use it, if I wanted the program to be better optimized; the "why" of it was irrelevant information. Rob Show quote "Ralph" <nt_consultin***@yahoo.com> wrote in message news:eAWi%23JTMIHA.2432@TK2MSFTNGP04.phx.gbl... > There is little mystery surrounding the optimization settings. Remember that > they are only a 'request' to the compiler to run (or avoid) certain > optimizers. If the compiler can't comply nothing happens. Most of the time > one can easily determine what may improve or what may decrease performance. > > For example, moving the 'a' variable to the module level removed it from the > realm of automatic variables to a default data segment, thus external to the > routine. You will find most optimizations work best with local variables > that the compiler can play with. (Like putting them in a register.) > Something along the same line happens when you place multiple loops, reusing > the same variables, within a single routine. > > While not that germane here - you might take a look at "aliasing" sometime. > Which often because of VB's love of references often precludes various > optimizations. > > -ralph "Robert Morley" <rmor***@magma.ca.N0.Freak1n.sparn> wrote in message level made it slower. I certainly *was* surprised whennews:%23xSq2AWMIHA.1188@TK2MSFTNGP04.phx.gbl... > Yeah, I wasn't really surprised by the fact that moving the variable up a > removing integer overflow checks made the program run slower...don't tell me there's "no mystery" there! :-)> a problem, though. You should still be able to use the> I don't understand why multiple loops in the same routine would have posed > same code, regardless whether it was one loop per routine or three in the same one...but I suppose compilers can't always understand> how we intend for them to interpret things. time ago, though I don't remember the specifics now. All I> > As for aliasing, I remember looking up why aliasing was a problem some > needed to know was that I pretty much never use it, and shouldn't use it, if I wanted the program to be better optimized; the "why"> of it was irrelevant information. Forget the 'aliasing'. My brain tends to take side trips towards anologies> > that aren't necessary. <g> Multiple loops or multple selects are always a problem because the optimizers likes to confine its 'maps' to as small a region as possible. The Integer check is interesting because like you I assumed that it it merely removed a conditional from the code. ie, instead of ... Do some math Jump if Overflow Result You get Do some math Result The documentation seems to back up that assumption. But with a few preliminary checks just now - I found not only the Jump (jo) missing but the opcodes are a bit different as well. ??? So I will grant you a "mystery" until I can isolate what I'm looking at. -ralph > But with a few preliminary checks just now - I found not only the Jump (jo) I thought of picking apart the EXE, but my 80x86 is a little rusty (which analogy is like saying that an already-rusty, leaky bucket > missing but the opcodes are a bit different as well. ??? > So I will grant you a "mystery" until I can isolate what I'm looking at. with more holes than bucket is "a little rusty"). If you're not already using it, can I suggest IDA Pro? Excellent intelligent disassembler, though it can be quite a challenge to understand how it works at times. Rob "Kelly Ethridge" <ke***@kellyethridge.com> wrote in message Actually when you're timing operations that take a very small amount of time news:%236k2PiNMIHA.2268@TK2MSFTNGP02.phx.gbl... > If you bust out each for..next loop into 3 different subs > you'll see significantly different results. (such as integer math) you need to take into account the effect of the timing mechanism itself. Also, for all timing tests it is usually better to time very short periods rather than long periods (in the "microseconds total" rather than in the "milliseconds or seconds total") because it is then far easier to detect whether the code was interrupted by the system at some point during the test and to rule out such results when determining the average. To see what I mean about taking into account the effect of the timing mechanism itself, try the following code (in a VB Form containing a Command Button) and run it as a compiled exe. On my machine I get a result of 21 microseconds for the complete loop. However, if I comment out the line "dummy1 = dummy1 + dummy2" (the code we are attempting to time) and thereby time a completely empty loop I still get a result of 14 microseconds. In other words, in this specific case each iteration of the loop itself takes twice as long as does the line of code we are attempting to time, thereby swamping the result. So, in such tests it is wise to run two loops, the first loop "empty" and the second loop containing the line of code you are attempting to time, and take the difference between the two results as the "real" result. In that way you will be able to see the real difference in the times of different lines of code. Go on, you know it makes sense ;-) Mike Option Explicit Private Declare Function QueryPerformanceFrequency _ Lib "kernel32" (lpFrequency As Currency) As Long Private Declare Function QueryPerformanceCounter _ Lib "kernel32" (lpPerformanceCount As Currency) As Long Private fullwidth As Long, fullheight As Long Private callTime As Currency Private Sub Command1_Click() Dim frequency As Currency Dim startTime As Currency Dim endTime As Currency Dim result As Double Dim n As Long, p As Long, dummy1 As Long, dummy2 As Long dummy1 = 1: dummy2 = 1 If QueryPerformanceFrequency(frequency) = 0 Then Exit Sub ' system doesn't support performance counter End If QueryPerformanceCounter startTime ' 1st call takes longer QueryPerformanceCounter startTime QueryPerformanceCounter endTime callTime = endTime - startTime ' time to perform a call ' QueryPerformanceCounter startTime ' place the code to time here For n = 1 To 10000 dummy1 = dummy1 + dummy2 Next n ' QueryPerformanceCounter endTime result = CDbl(endTime - startTime - callTime) / frequency result = CLng(result * 1000000) MsgBox result & " microseconds" End Sub I understand your point. My response was only in response about the
discrepancy of using the Integer Overflow optimization when everything was in a single method, not to time the 3 methods against each other. Mike Williams wrote: Show quote > "Kelly Ethridge" <ke***@kellyethridge.com> wrote in message > news:%236k2PiNMIHA.2268@TK2MSFTNGP02.phx.gbl... > >> If you bust out each for..next loop into 3 different subs >> you'll see significantly different results. > > Actually when you're timing operations that take a very small amount of > time (such as integer math) you need to take into account the effect of > the timing mechanism itself. Also, for all timing tests it is usually > better to time very short periods rather than long periods (in the > "microseconds total" rather than in the "milliseconds or seconds total") > because it is then far easier to detect whether the code was interrupted > by the system at some point during the test and to rule out such results > when determining the average. To see what I mean about taking into > account the effect of the timing mechanism itself, try the following > code (in a VB Form containing a Command Button) and run it as a compiled > exe. > > On my machine I get a result of 21 microseconds for the complete loop. > However, if I comment out the line "dummy1 = dummy1 + dummy2" (the code > we are attempting to time) and thereby time a completely empty loop I > still get a result of 14 microseconds. In other words, in this specific > case each iteration of the loop itself takes twice as long as does the > line of code we are attempting to time, thereby swamping the result. So, > in such tests it is wise to run two loops, the first loop "empty" and > the second loop containing the line of code you are attempting to time, > and take the difference between the two results as the "real" result. In > that way you will be able to see the real difference in the times of > different lines of code. > Go on, you know it makes sense ;-) > > Mike > > Option Explicit > Private Declare Function QueryPerformanceFrequency _ > Lib "kernel32" (lpFrequency As Currency) As Long > Private Declare Function QueryPerformanceCounter _ > Lib "kernel32" (lpPerformanceCount As Currency) As Long > Private fullwidth As Long, fullheight As Long > Private callTime As Currency > > Private Sub Command1_Click() > Dim frequency As Currency > Dim startTime As Currency > Dim endTime As Currency > Dim result As Double > Dim n As Long, p As Long, dummy1 As Long, dummy2 As Long > dummy1 = 1: dummy2 = 1 > If QueryPerformanceFrequency(frequency) = 0 Then > Exit Sub ' system doesn't support performance counter > End If > QueryPerformanceCounter startTime ' 1st call takes longer > QueryPerformanceCounter startTime > QueryPerformanceCounter endTime > callTime = endTime - startTime ' time to perform a call > ' > QueryPerformanceCounter startTime > ' place the code to time here > For n = 1 To 10000 > dummy1 = dummy1 + dummy2 > Next n > ' > QueryPerformanceCounter endTime > result = CDbl(endTime - startTime - callTime) / frequency > result = CLng(result * 1000000) > MsgBox result & " microseconds" > End Sub > > While this is quite true, for most of what I do, I prefer to time "real-world" conditions, rather than microcosm conditions. In
this case, that's admittedly not such a good plan, but with VB frequently optimizing useless code out of existence, I wasn't sure if timing an empty loop would actually produce useful information. Rob "Mike Williams" <mi***@whiskyandCoke.com> wrote in message news:unhcUpTMIHA.2268@TK2MSFTNGP02.phx.gbl... <snipped>> Actually when you're timing operations that take a very small amount of time (such as integer math) you need to take into account > the effect of the timing mechanism itself. Also, for all timing tests it is usually better to time very short periods rather than > long periods (in the "microseconds total" rather than in the "milliseconds or seconds total") because it is then far easier to > detect whether the code was interrupted by the system at some point during the test and to rule out such results when determining > the average. To see what I mean about taking into account the effect of the timing mechanism itself, try the following code (in a > VB Form containing a Command Button) and run it as a compiled exe. |
|||||||||||||||||||||||