From: Mike Williams on 1 Oct 2009 18:59 "Tom Shelton" <tom_shelton(a)comcastXXXXXXX.net> wrote in message news:eeWP5NuQKHA.1876(a)TK2MSFTNGP06.phx.gbl... > But, again, the preformance difference is in factions of a second. > Not even worth talking about outside of news groups. In percentage terms it is a lot, with the VB6 .bmp colour counting code running about five times faster than the VB.Net code, regardless of the fact that it is just fractions of a second for a single relatively small image. > It would be trivial really to just read the bitmap data directly > from the bitmap file . . . Yes, in fact that's what I was going to do, and it would have resulted in a small speed increase, except that I intended to eventually add the code to handle jpegs and other bitmap images etc and so I decided to load the bmp into a DIBSection (which in any case is almost the same thing) so that the code would still work when I eventually added code to load and decode a jpg into a DIB. > . . . rather then use the bitmap class, etc - but the bitmap class > can handle bmp, gif, png, etc, etc. Like with most things - if > speed is unacceptable, then I find the bottle neck and then > see if there is a faster way to accomplish it. The bottleneck is in your For Next loop code, not in the part that appears to be loading the image using the bitmap class or whatever. Try moving the start timer to immediately before the start of the For Next loop to see what I mean. The bottleneck definitely appears to be inside the For Next loop, probably the stuff dealing with the Dictionary. > I agree that people shouldn't be making all kinds of speed > claims - but, it goes both ways. Yes, it does. That's why I've always said that if the likes of McCarthy and Clark and Ligthert stop deliberately causing trouble in the VB6 group then I (and presumably others) will immediately stop retaliating :-) Mike
From: Tom Shelton on 1 Oct 2009 19:40 On 2009-10-01, Mike Williams <Mike(a)WhiskyAndCoke.com> wrote: > "Tom Shelton" <tom_shelton(a)comcastXXXXXXX.net> wrote in message > news:eeWP5NuQKHA.1876(a)TK2MSFTNGP06.phx.gbl... > >> But, again, the preformance difference is in factions of a second. >> Not even worth talking about outside of news groups. > > In percentage terms it is a lot, with the VB6 .bmp colour counting code > running about five times faster than the VB.Net code, regardless of the fact > that it is just fractions of a second for a single relatively small image. > >> It would be trivial really to just read the bitmap data directly >> from the bitmap file . . . > > Yes, in fact that's what I was going to do, and it would have resulted in a > small speed increase, except that I intended to eventually add the code to > handle jpegs and other bitmap images etc and so I decided to load the bmp > into a DIBSection (which in any case is almost the same thing) so that the > code would still work when I eventually added code to load and decode a jpg > into a DIB. > >> . . . rather then use the bitmap class, etc - but the bitmap class >> can handle bmp, gif, png, etc, etc. Like with most things - if >> speed is unacceptable, then I find the bottle neck and then >> see if there is a faster way to accomplish it. > > The bottleneck is in your For Next loop code, not in the part that appears > to be loading the image using the bitmap class or whatever. Try moving the > start timer to immediately before the start of the For Next loop to see what > I mean. The bottleneck definitely appears to be inside the For Next loop, > probably the stuff dealing with the Dictionary. > Ah, that very well could be. I'll play with that bit. One problem is probably the use of bitconverter as well. changing that line alone to Dim color As Integer = RGB(bytes(i), bytes(i + 1), bytes(i + 1)) lowers the execution time to: Counted 131763 unique colors in 00:00:00.0940000 Counted 131763 unique colors in 00:00:00.0780000 Counted 131763 unique colors in 00:00:00.0620000 Counted 131763 unique colors in 00:00:00.0630000 Counted 131763 unique colors in 00:00:00.0780000 Counted 131763 unique colors in 00:00:00.0620000 Counted 131763 unique colors in 00:00:00.0630000 Counted 131763 unique colors in 00:00:00.0620000 Counted 131763 unique colors in 00:00:00.0630000 Counted 131763 unique colors in 00:00:00.0620000 Average Time: 00:00:00.0690000 Press any key to continue . . . So, this maybe an optimization issue. The dictionary is very fast at retrieving, but is slower adding because it is a hash table. let me try a couple of more changes - then maybe this might be better. >> I agree that people shouldn't be making all kinds of speed >> claims - but, it goes both ways. > > Yes, it does. That's why I've always said that if the likes of McCarthy and > Clark and Ligthert stop deliberately causing trouble in the VB6 group then I > (and presumably others) will immediately stop retaliating :-) Mike - you and yours cause as much trouble as we .net'rs do. You invite the problems by the way you malign .net when people accidently post. Can't you just redirect and let it go? You and mayayanna are the worst that way. -- Tom Shelton
From: Mike Williams on 2 Oct 2009 04:48 "Tom Shelton" <tom_shelton(a)comcastXXXXXXX.net> wrote in message news:ONBxECvQKHA.4244(a)TK2MSFTNGP06.phx.gbl... >> [Mike said] The bottleneck is in your For Next loop code, not in the >> part that appears to be loading the image using the bitmap class or >> whatever. The bottleneck definitely appears to be inside the For Next >> loop, probably the stuff dealing with the Dictionary. > > [Tom said] Ah, that very well could be. I'll play with that bit. One > problem is probably the use of bitconverter as well. changing that > line alone [code snipped] to lowers the execution time to: > Counted 131763 unique colors in 00:00:00.0620000 [average] Yep, that seems to have brought it down somewhat, but of course the main bottleneck still appears to be the dictionary. > So, this maybe an optimization issue. The dictionary is very fast > at retrieving, but is slower adding because it is a hash table. let > me try a couple of more changes - then maybe this might be better. Okay. But don't worry about it too much. I think we've already posted too many messages in this thread already :-). Personally I think you'll need to get rid of the dictionary altogether if you want to coax a lot more speed out of it. I know in my case getting the original major bottleneck out of the way was relatively easy, requiring only fairly small changes in code, but trimming off the smaller bottlenecks to "see if we can just squeeze a few more milliseconds out of this thing" was a lot harder. For example, my original code had just eight lines of code inside the For Next loop (where p is a VB Long and TwoToThePowerOf is small "look up" array containing eight Bytes): For j = 1 To SourceWidth * SourceHeight * 3 Step 3 p = &H10000 * SourceArray(j) + &H100& * SourceArray(j + 1) + SourceArray(j + 2) allclrsByte = p \ 8 bitmask = TwoToThePowerOf(7 - p Mod 8) z = clrs(allclrsByte) If (z And bitmask) = 0 Then used = used + 1 clrs(allclrsByte) = z Or bitmask End If Next j In fact my original testbed code was even much smaller than the above, because most of the 8 code lines in the above loop are concerned with using individual bits (rather than whole bytes or whatever) to record each colour actually used. Anyway, the above loop produced an overall code time of about 0.021, with about 0.005 of that taken up by LoadImage and the remaining 0.016 taken by the loop. Then I began to think that I could squeeze a few more milliseconds out of that by getting rid of the three individual Byte array reads and the math in the line in the first code line within the loop. In order to do that I decided to address the data using VB6 Longs instead of Bytes, with one Long reading three bytes of data and masking out the unwanted byte. Seems reasonable except for the fact that using a VB6 array of Longs allows you to step one long (or more than one Long) at a time through the array, whereas I wanted to step just 3 bytes (VB6 doesn't have any of this fancy stepping a Long through a Byte array any number of bytes at a time that judging by your own code you appear to have in .Net), and a copymemory in the loop was out of the question because it would be too slow. So, in order to perform the trick I wanted to perform and to do it in a fast way I needed to persuade VB6 to step a Long through an array of byte data three bytes at a time, which VB6 cannot do and which required me to mess about using all the SafeArray stuff to point four separate VB6 Long arrays all at slightly different points in the same single block of data bytes. That caused the code in the loop to grow from just 8 lines to a whopping 68 lines! In addition to that there were all the additional declarations and things that were required outside the loop, adding even more lines of code. Anyway, the result was some extremely long (and I must admit quite rambling at the moment!) code, with the 68 line loop actually executing about 0.006 seconds faster than the previous 8 line loop, resulting in the loop time changing from 0.016 to 0.010 seconds and changing the overall time from 0.021 seconds to about 0.015 seconds. This behaviour of ever diminishing returns for ever more additional code probably applies to most programming languages when attempting to squeeze out those extra few milliseconds, and in my case it produced an extremely rambling mess of spaghetti (because I was concentrating on testing the theory rather than writing neat code), but it does work very fast. I'm sure that you will be able to squeeze similar performance out of your VB.Net code once you start tweaking it (although I'm fairly sure you will need to get rid of the dictionary in order to do so) but as far as I am concerned, even if you do, I will have managed to prove my point in my argument with Cor Ligthert. > Mike - you and yours cause as much trouble as we .net'rs do. > You invite the problems by the way you malign .net when > people accidently post. Yes, some of us sometimes do that, but the catalyst for that behaviour was the appearance on the VB6 group of certain dotnetters who were specifically out to cause trouble, many of whom derided VB6 programmers in the group and called them last century dummies who were stuck with VB6 because they were incapable of learning anything else, which is most definitely not true. > just redirect and let it go? Yes. I'll start doing that immediately. In fact I'll stop posting any of the messages to which you refer, but I'll only do it if the dotnetters who are currently deliberately attempting to cause trouble in the VB6 group also immediately stop doing it. Seems fair to me. Anyway, I think this thread can be considered closed now. It's long enough already. I'd still like to know how that compiled exe I sent you runs at your end though, and how much speed to manage to squeeze out of your net code when the dictionary is removed. It's been fun, but I think it's time to go now ;-) Mike
From: Mike Williams on 3 Oct 2009 08:37 "Tom Shelton" <tom_shelton(a)comcastXXXXXXX.net> wrote in message news:euEnpegQKHA.4692(a)TK2MSFTNGP06.phx.gbl... > That is not the results I'm getting at all... I'm not sure what your > doing > here. but on my machine - maximized at 1680x1050 with the drawing code > removed from the rowcomplete in the vb.net code... > > VB6: > MT: 5.30 sec > ST: 6.55 sec > > VB.NET: > MT: 1.203 sec > ST: 2.344 sec Just for the record, as has since been established, the figures you quote above were achieved when you inadvertently left the picSrf.Refresh in Olaf Schmidt's code, so that you were running it while it was still peforming graphic operations whereas you were running your own VB.Net code when it was not doing so. After commenting out the picSrf.Refresh in Olaf's code you discovered that the figures were very different. In fact, under those conditions on my own 2.4 Ghz Intel machine with the Form maximized on a 1680 x 1050 display (similar setup to your own) Olaf's code gives me: VB6: MT: 1.32 sec ST: 2.66 sec Mike
From: Mike Williams on 3 Oct 2009 08:37
"Schmidt" <sss(a)online.de> wrote in message news:e4zZaR$QKHA.1372(a)TK2MSFTNGP02.phx.gbl... > [Addressed to Tom Shelton] Looks not right (yet) to > me (your MT-result). With entirely disabled GDI- > refreshs, the timing should scale nearly lineary with two > threads (on a DualCore).Y our 2.77 seconds for the > singlethreaded run look more plausible anyways... > But on my machine the two-threaded timing scales > down to nearly exactly the half of the singlethreaded > timing - would mean - you should get about: > ST: 2.77 / 2 = MT: 1.39 seconds on your 2.4 GHz-Dualcore. Your calculations seems to be spot on there, Olaf. I'm using a 2.4 Ghz processor (the same 2.4 GHz Intel 6600 that I believe Tom Shelton uses, except mine is a quad core whereas his is a dual core) and when running maximized at the same 1680 x 1050 resolution that I believe Tom uses your VB6 code gives me: VB6: MT: 1.32 sec ST: 2.66 sec The only reason I can think of why Tom Shelton's dual core is not scaling linearly between running single or multi thread is perhaps when running your code he has some background task running which is using a fair amount of processor time? Mike |