473,785 Members | 2,789 Online
Bytes | Software Development & Data Engineering Community
+ Post

Home Posts Topics Members FAQ

How expensive is brush creation?

I am doing quite a bit of custom painting and it means I have to
create a lot of brushes (think one for every file system object in a
directory) per paint. How expensive is this? Should I find a way to
create the brushes once, store them in an member variable, and use
them when I need them? Or is creating brushes a throw-away process
that doesn't take a lot of work?

Thanks for the info.

Tom P.
Aug 5 '08
31 3417
On 5 août, 21:17, "Tom P." <padilla.he...@ gmail.comwrote:
On Aug 5, 2:09*pm, "Peter Duniho" <NpOeStPe...@nn owslpianmk.com>
wrote:


On Tue, 05 Aug 2008 11:49:44 -0700, Tom P. <padilla.he...@ gmail.comwrote:
I'm sorry, I must have misspoke. I don't create a thousand different
brushes, I only create about 6 or 9 different brushes... hundreds of
times. [...]
Right, I finally figured that out. *:) *I might just not have been reading *
carefully enough the first time.
I don't think that caching a dozen or so brushes long-term should be an*
issue, if you decide that's a viable design change. *That's not enough to *
cause any serious problems with resource consumption, I think.
Still, I wouldn't bother until if and when you find an actual performance *
problem. *Just remember to dispose any brushes you create, and you'll*
probably be fine.
Pete

Thanks for the help guys. Pete is right, I should have done this
sooner but I was stuck thinking about something from one direction.
Thanks to Michel for giving me the kick in the head to realize how
simple a short test could be.

Using the following code...

for (long loop = 0; loop 1000000000;loop ++ )
* * * * * * {
* * * * * * * * Rectangle tempRect = new Rectangle(0,0,1 00, 18);

* * * * * * * * tempBrush = new LinearGradientB rush(tempRect,
Color.Blue, Color.Red, 0.01F) ;
* * * * * * * * tempBrush = null;
* * * * * * }

...takes 0.00013344 secs. (timed using the hardware HiRes API timer).

I think I can spare 0.00013344 secs.

Sorry Pete.

Tom P.- Masquer le texte des messages précédents -

- Afficher le texte des messages précédents -
Er... Did you copy/paste from Visual Studio ? Because if you did,
maybe you should try again, changing the ">" into a "<"... and remove
three zeros in your loop, otherwise you'll still be waiting
tomorrow... Prepare to be surprised !

Michel
Aug 5 '08 #21
On 5 août, 21:53, "Peter Duniho" <NpOeStPe...@nn owslpianmk.comw rote:
On Tue, 05 Aug 2008 12:39:59 -0700, <michel.desang. ..@gmail.comwro te:
The only evidence I have is "Effective C#" by Bill Wagner, in which
chapter 16, "Minimize Garbage", deals with the handling of brushes in
paint handlers.

Well, I don't know anything about that book. *But you should be careful*
about believing everything you read, as well as about what you apply it to.
Maybe you should read it before advising anything, or assuming it's
some sort of "dummies book"? Also, exactly what makes you think I'm
the credulous type, or have less experience than you have, or am less
cautious in the way I acquire new information?
It's trivially true (and thus uninteresting) that it's faster to not do *
something than to do it. *But that doesn't mean that the act of doing it *
is a significant cost that warrants complicating the code just so you can*
avoid doing it.
I was speaking about this particular case, not in general. The time
saved should be significant enough to warrant *simplifying* the code.
[...]
Oh, and Brush and SolidBrush both implement IDisposable and inherit
from MarshalByRef. So, let me disagree completely with you on that GC
matter...

I have no idea what you mean. *Even if I hadn't specifically pointed out *
that the object needs to be disposed (which I in fact did), what's that *
got to do with whether or not the memory management overhead is *
significant? *What's your point?
This is a reference type (harder on the GC than value types), which
implements IDisposable (two method calls, including
GCSuppressFinal ize), and marshalls its data accross boundaries (which
is, sorry to be trivial, longer than not marshalling data accross
boundaries).

In the end, exactly what's your problem with me saying that allocating
unnecessary objects is unnecessary and, in this case, expensive? Could
you explain in simple terms? Did it rub you the wrong way?

Michel
Aug 5 '08 #22
On Tue, 05 Aug 2008 13:09:30 -0700, <mi************ **@gmail.comwro te:
Maybe you should read it before advising anything, or assuming it's
some sort of "dummies book"? Also, exactly what makes you think I'm
the credulous type, or have less experience than you have, or am less
cautious in the way I acquire new information?
What makes you think I think any of that?

I'm simply pointing out that the quote you included doesn't change
anything I wrote.
>It's trivially true (and thus uninteresting) that it's faster to not do
Â*
something than to do it. Â*But that doesn't mean that the act of doing
it Â*
is a significant cost that warrants complicating the code just so you
can Â*
avoid doing it.

I was speaking about this particular case, not in general. The time
saved should be significant enough to warrant *simplifying* the code.
Why? What makes you think it "should be significant enough"? Did you
measure it in the real-world context?

If you have specific facts, please share them. If you don't, then you
have no basis for arguing in favor of complicating the design. And yes,
it's a complication to change from simply allocating objects as needed to
caching them over time. I don't see any justification for your claim that
the change could be described as "*simplifyi ng* the code".
[...]
Oh, and Brush and SolidBrush both implement IDisposable and inherit
from MarshalByRef. So, let me disagree completely with you on that GC
matter...

I have no idea what you mean. Â*Even if I hadn't specifically pointed
out Â*
that the object needs to be disposed (which I in fact did), what's that
Â*
got to do with whether or not the memory management overhead is Â*
significant? Â*What's your point?

This is a reference type (harder on the GC than value types),
Huh? Value types aren't managed by the GC at all. That parenthetical
statement makes no sense at all. At the very most, it's trivially true
(and so again, uninteresting).
which
implements IDisposable (two method calls, including
GCSuppressFinal ize), and marshalls its data accross boundaries (which
is, sorry to be trivial, longer than not marshalling data accross
boundaries).
So what? None of that increases the _garbage collector's_ workload. The
object itself has more overhead, yes. But that wasn't the point.
In the end, exactly what's your problem with me saying that allocating
unnecessary objects is unnecessary and, in this case, expensive? Could
you explain in simple terms? Did it rub you the wrong way?
You are the one who seems to be rubbed the wrong way. I am simply
pointing out that there's no evidence at all that Tom's original "allocate
as needed" design is in need of changing (other than using the pre-defined
brushes where possible, which I already agree with you about).

If he's measured the cost and found his application is spending too much
time drawing these items, then yes...there's some value in exploring other
designs that don't allocate these objects over and over again. But a)
even if he found some performance cost that needed fixing, it's
_extremely_ unlikely that it would be related to the GC (i.e. you'd find
the same cost just creating GDI brushes in unmanaged code), and b) so far
there's been no demonstration of such a performance cost in need of fixing.

Pete
Aug 5 '08 #23
On 5 août, 22:20, "Peter Duniho" <NpOeStPe...@nn owslpianmk.comw rote:
On Tue, 05 Aug 2008 13:09:30 -0700, <michel.desang. ..@gmail.comwro te:
Maybe you should read it before advising anything, or assuming it's
some sort of "dummies book"? Also, exactly what makes you think I'm
the credulous type, or have less experience than you have, or am less
cautious in the way I acquire new information?

What makes you think I think any of that?
The sentence you snipped : "you should be careful about believing
everything you read, as well as about what you apply it to".
I'm simply pointing out that the quote you included doesn't change *
anything I wrote.
It's trivially true (and thus uninteresting) that it's faster to not do *
*
something than to do it. *But that doesn't mean that the act of doing *
it *
is a significant cost that warrants complicating the code just so you *
can *
avoid doing it.
I was speaking about this particular case, not in general. The time
saved should be significant enough to warrant *simplifying* the code.

Why? *What makes you think it "should be significant enough"? *Did you *
measure it in the real-world context?
Yep, see the loop example above.
If you have specific facts, please share them. *If you don't, then you *
have no basis for arguing in favor of complicating the design. *And yes, *
it's a complication to change from simply allocating objects as needed to*
caching them over time. *I don't see any justification for your claim that *
the change could be described as "*simplifyi ng* the code".
I don't see any justification for your claim that declaring a static
member variable is more complicated than allocating several instance
ones.
[...]
Oh, and Brush and SolidBrush both implement IDisposable and inherit
from MarshalByRef. So, let me disagree completely with you on that GC
matter...
I have no idea what you mean. *Even if I hadn't specifically pointed*
out *
that the object needs to be disposed (which I in fact did), what's that *
*
got to do with whether or not the memory management overhead is *
significant? *What's your point?
This is a reference type (harder on the GC than value types),

Huh? *Value types aren't managed by the GC at all. *That parenthetical *
statement makes no sense at all. *At the very most, it's trivially true*
(and so again, uninteresting).
Lol ! So it's nonsensical BUT trivially true. Reminds me of this :
http://thedailywtf.com/Articles/What...uth_0x3f_.aspx
which
implements IDisposable (two method calls, including
GCSuppressFinal ize), and marshalls its data accross boundaries (which
is, sorry to be trivial, longer than not marshalling data accross
boundaries).

So what? *None of that increases the _garbage collector's_ workload. *The *
object itself has more overhead, yes. *But that wasn't the point.
Er... I didn't say those two points increased the GC workload, *you*
assumed I did (reread the sentence); I was talking about the
allocation/deallocation overhead, and THAT was the point of the OP.
In the end, exactly what's your problem with me saying that allocating
unnecessary objects is unnecessary and, in this case, expensive? Could
you explain in simple terms? Did it rub you the wrong way?

You are the one who seems to be rubbed the wrong way. *I am simply *
pointing out that there's no evidence at all that Tom's original "allocate *
as needed" design is in need of changing (other than using the pre-defined *
brushes where possible, which I already agree with you about).
Argumentum ad ignorantiam : http://en.wikipedia.org/wiki/Argument_from_ignorance

You do a lot of those !
If he's measured the cost and found his application is spending too much *
time drawing these items, then yes...there's some value in exploring other *
designs that don't allocate these objects over and over again. *But a) *
even if he found some performance cost that needed fixing, it's *
_extremely_ unlikely that it would be related to the GC (i.e. you'd find *
the same cost just creating GDI brushes in unmanaged code), and b) so far*
there's been no demonstration of such a performance cost in need of fixing.
a) Some random writer, apparently a professionnal programmer, seems to
strongly disagree with you, and has even written a chapter about that
in his book; and I should add that "unlikely that it would be related
to the GC" is pretty silly (the GC workload is directly related to the
number of objects created/destroyed, AND DON'T PICK ON THAT ONE, I
mean objects as in reference types), and b) yes there is, try my loop,
and his loop once you correct the typo.

In short, you're trying to establish that he shouldn't try to improve
his program, based on several assumptions on your part : he's using
only a few brushes, the program won't run for long, the paint event
won't be called often, etc.

So, again : yes, Tom, you should go the extra mile to make your
brushes static for a lot of reasons : your code will be clearer,
faster, will use less memory, will spend less time in the GC, and you
will learn good habits in the process.

And, Pete, people who say "All the more reason to not do that unless
you know for sure you have to" shouldn't be giving tips to people who
write, create, invent or try to discover or improve. Programmers ?

Michel
Aug 5 '08 #24
On Aug 5, 2:57*pm, michel.desang.. .@gmail.com wrote:
On 5 août, 21:17, "Tom P." <padilla.he...@ gmail.comwrote:
On Aug 5, 2:09*pm, "Peter Duniho" <NpOeStPe...@nn owslpianmk.com>
wrote:
On Tue, 05 Aug 2008 11:49:44 -0700, Tom P. <padilla.he...@ gmail.comwrote:
I'm sorry, I must have misspoke. I don't create a thousand different
brushes, I only create about 6 or 9 different brushes... hundreds of
times. [...]
Right, I finally figured that out. *:) *I might just not have been reading *
carefully enough the first time.
I don't think that caching a dozen or so brushes long-term should be an *
issue, if you decide that's a viable design change. *That's not enough to *
cause any serious problems with resource consumption, I think.
Still, I wouldn't bother until if and when you find an actual performance *
problem. *Just remember to dispose any brushes you create, and you'll *
probably be fine.
Pete
Thanks for the help guys. Pete is right, I should have done this
sooner but I was stuck thinking about something from one direction.
Thanks to Michel for giving me the kick in the head to realize how
simple a short test could be.
Using the following code...
for (long loop = 0; loop 1000000000;loop ++ )
* * * * * * {
* * * * * * * * Rectangle tempRect = new Rectangle(0,0,1 00, 18);
* * * * * * * * tempBrush = new LinearGradientB rush(tempRect,
Color.Blue, Color.Red, 0.01F) ;
* * * * * * * * tempBrush = null;
* * * * * * }
...takes 0.00013344 secs. (timed using the hardware HiRes API timer).
I think I can spare 0.00013344 secs.
Sorry Pete.
Tom P.- Masquer le texte des messages précédents -
- Afficher le texte des messages précédents -

Er... Did you copy/paste from Visual Studio ? Because if you did,
maybe you should try again, changing the ">" into a "<"... and remove
three zeros in your loop, otherwise you'll still be waiting
tomorrow... Prepare to be surprised !

Michel
Nope, taken right out of the VS-IDE and pasted in here. If you want
the entire code I suppose I could paste it here as well.

the HiRes timer uses...
[DllImport("kern el32.dll")]
internal extern static UInt32 QueryPerformanc eCounter(ref Int64
lpPerformanceCo unt);

... to get the timings.

Tom P.
Aug 5 '08 #25
On Tue, 05 Aug 2008 13:52:42 -0700, <mi************ **@gmail.comwro te:
On 5 août, 22:20, "Peter Duniho" <NpOeStPe...@nn owslpianmk.comw rote:
>On Tue, 05 Aug 2008 13:09:30 -0700, <michel.desang. ..@gmail.comwro te:
Maybe you should read it before advising anything, or assuming it's
some sort of "dummies book"? Also, exactly what makes you think I'm
the credulous type, or have less experience than you have, or am less
cautious in the way I acquire new information?

What makes you think I think any of that?

The sentence you snipped : "you should be careful about believing
everything you read, as well as about what you apply it to".
Do you disagree with the sentence? If not, I don't see what your problem
is. The quote you provided is nothing as compared to a real-world test.
[...]
I was speaking about this particular case, not in general. The time
saved should be significant enough to warrant *simplifying* the code.

Why? Â*What makes you think it "should be significant enough"? Â*Did you Â*
measure it in the real-world context?

Yep, see the loop example above.
The loop in which you forgot to dispose the brush you allocated, forcing
the GC to have to do finalization on them (eventually)? And yet in which
you still were able to create 1,000,000 in a second? At 1000 brushes per
frame (per Tom's comments), that's 1000 frames per second, about ten times
faster than any typical computer display can handle. Even if Tom upped
his brush count to 10,000 Brush instances per frame, he could still draw
100 frames in a second. That's plenty fast for a 1st-person-shooter,
never mind an application displaying information about a file system.

And of course, all that assumes that brush creation accounts for the vast
majority of time spent drawing, which is unlikely. So in practice it's
even more absurd to worry about the performance of the Brush
creation/destruction than demonstrated by your own analysis.

Again, where's the performance problem here?
[...]
I don't see any justification for your claim that declaring a static
member variable is more complicated than allocating several instance
ones.
I never suggesting "allocating [sic]" instance variables. My impression
of Tom's design is that he's allocating brushes in a method, storing them
in a local variable just long enough for that method to execute. My
suggestion was that there's nothing fundamentally wrong with that design.
The only reference to "static" I made was in the context of an object that
remains allocated (i.e. "statically ") rather than being recreated with
each use (i.e. "dynamicall y").

My use of the word has nothing to do with static or instance members of
classes. A long-term cache of brushes could in fact be implemented either
way (i.e. stored in static or instance members), but that's not what I'm
talking about at all.
[...]
This is a reference type (harder on the GC than value types),

Huh? Â*Value types aren't managed by the GC at all. Â*That parenthetical Â*
statement makes no sense at all. Â*At the very most, it's trivially true
Â*
(and so again, uninteresting).

Lol ! So it's nonsensical BUT trivially true.
"At the very most", it's trivially true. In practice, since the GC
doesn't manage value types at all, it's nonsensical to compare the
difficulty of the GC in managing reference types versus value types.

I'm sorry you don't comprehend the subtleties in my statement. But the
fact remains, it doesn't make sense to discuss how "hard" management of
value types is on the garbage collector. The GC just doesn't manage them
at all.

Yes, in a sense that means it's no work at all for the GC. But only in
the same sense that it's no work at all for you to mow my lawn. Do you
really think it makes sense to talk about how much harder it is for you to
mow your own lawn than mine, given that you don't do the latter at all?
[...]
>So what? Â*None of that increases the _garbage collector's_ workload.
The Â*
object itself has more overhead, yes. Â*But that wasn't the point.

Er... I didn't say those two points increased the GC workload, *you*
assumed I did (reread the sentence); I was talking about the
allocation/deallocation overhead, and THAT was the point of the OP.
This whole sub-thread started here:

On Tue, 05 Aug 2008 11:27:00 -0700, Peter Duniho
<Np*********@nn owslpianmk.comw rote:
On Tue, 05 Aug 2008 11:12:01 -0700, <mi************ **@gmail.comwro te:
>It is VERY expensive, not because of the brushes themselves, but
because you're feeding the Garbage Collector with all those brushes on
every Paint event.

The GC design is optimized to handle repeated allocation and discarding
of short-lived objects. GC is not an issue here at all, though disposal
of brushes _theoretically_ might be. I doubt most code would see any
issue.
As you can see, my only contribution here has always been about the GC
overhead. Nothing more. If you choose to infer a broader discussion,
that's your mistake. If you choose to inject comments irrelevant to the
original discussion, don't expect me to find them relevant.
>
In the end, exactly what's your problem with me saying that allocating
unnecessary objects is unnecessary and, in this case, expensive? Could
you explain in simple terms? Did it rub you the wrong way?

You are the one who seems to be rubbed the wrong way. Â*I am simply Â*
pointing out that there's no evidence at all that Tom's original
"allocate Â*
as needed" design is in need of changing (other than using the
pre-defined Â*
brushes where possible, which I already agree with you about).

Argumentum ad ignorantiam :
http://en.wikipedia.org/wiki/Argument_from_ignorance
Uh. You should probably read that Wikipedia article more closely. It has
nothing to do with this discussion. From a purely practical matter, it
makes no sense to optimize code until you know it's a piece of code in
need of optimizing. This is completely different from "argumentum ad
ignorantiam".
You do a lot of those !
Ad hominem will get you nowhere.
[...]
a) Some random writer, apparently a professionnal programmer, seems to
strongly disagree with you,
Well, technically I disagree with him. But whatever.
and has even written a chapter about that
in his book;
The fact that it's in print doesn't mean it's true, never mind applicable
to the implementation at hand.
and I should add that "unlikely that it would be related
to the GC" is pretty silly
I didn't write that. I wrote "_extremely _ unlikely...".
(the GC workload is directly related to the
number of objects created/destroyed, AND DON'T PICK ON THAT ONE,
Why not? It's patently false. The workload is not _directly_ related to
the number of objects created/destroyed. In fact, short-lived objects
incur a MUCH lower per-object cost to the GC than
long-lived-but-still-transient objects (that is, objects that age out of
generation 0).

There is not a direct correlation. There's an indirect relationship, but
no direct correlation.

More importantly, whether there's a direct correlation or not, it's the
actual _cost_ that's at issue here. And even if the cost was directly
proportional to the number of objects, the per-object cost is so tiny
relative to what else is going on in the code, the GC overhead is
"_extremely _ unlikely" to be significant.
I mean objects as in reference types), and b) yes there is, try my loop,
and his loop once you correct the typo.
Your loop still has a bug in it, but even so it fails to prove that the GC
cost is significant. It's much more likely that the cost of allocating
and disposing the _unmanaged_ resources overwhelms whatever insignificant
cost the GC incurs.

You can do the test yourself. Time these two loops and compare:

for (long i = 0; i < 1000000; i++)
{
object obj = new object();
}

and:

for (long i = 0; i < 1000000; i++)
{
using (Brush brush = new SolidBrush(Colo r.Blue))
{
}
}

On my computer, the second completes in about 1.1 seconds (similar to your
results). The first completes in about 0.02 seconds.

In other words, in a loop that is _only_ creating and destroying a Brush,
the GC-related activity incurs only 2% of the total cost of the loop.
That's before doing _anything_ else interesting in the loop.

No, it's pretty clear: when dealing with the Brush class, most of the cost
incurred managing the object has nothing to do with the GC. Inasmuch as
there's any expense at all, it's the object itself that is costly (and as
your own test shows, it's not even that costly, when you compare it to
what is considered a reasonable frame rate from the user's point of view).

I'm sorry you took such offense at my point of correction to your original
statement, and I'm especially sorry that it's taking so much effort to
explain myself. But facts are facts.
In short, you're trying to establish that he shouldn't try to improve
his program, based on several assumptions on your part : he's using
only a few brushes, the program won't run for long, the paint event
won't be called often, etc.
No. I _am_ establishing that he shouldn't bother _changing_ his program
until he has some specific indication that doing so would be an
_improvement_. And I've made none of the assumptions that you claim I
have (in fact, quite the opposite).

You are engaging in tautology, having assumed that the change would be an
improvement before you have actually proven it to be so.
So, again : yes, Tom, you should go the extra mile to make your
brushes static for a lot of reasons : your code will be clearer,
faster, will use less memory, will spend less time in the GC, and you
will learn good habits in the process.

And, Pete, people who say "All the more reason to not do that unless
you know for sure you have to" shouldn't be giving tips to people who
write, create, invent or try to discover or improve. Programmers ?
Believe that at your own peril. You're going to waste a lot of time
optimizing code and making it more complicated for no useful benefit.

Pete
Aug 5 '08 #26
On Tue, 05 Aug 2008 14:36:15 -0700, Tom P. <pa***********@ gmail.comwrote:
[...]
Using the following code...
for (long loop = 0; loop 1000000000;loop ++ )
[...]

Er... Did you copy/paste from Visual Studio ? Because if you did,
maybe you should try again, changing the ">" into a "<"... and remove
three zeros in your loop, otherwise you'll still be waiting
tomorrow.. Prepare to be surprised !

Michel

Nope, taken right out of the VS-IDE and pasted in here. If you want
the entire code I suppose I could paste it here as well.
Right. His point is that since that's exactly the code you used to test
performance, it's not a useful test. Your loop doesn't even execute one
iteration. It will exit as soon as the condition "loop 1000000000" is
false, which it is on the very first comparison.

That said, his own test does a fine job demonstrating just how pointless
it is to worry about the cost of creating and destroying Brush instances.
You can do a million per second. It's highly unlikely that you'd put
enough information up on the screen at once for the user to be affected by
how long it takes to create and destroy a Brush instance.

Pete
Aug 5 '08 #27
On 5 août, 23:36, "Tom P." <padilla.he...@ gmail.comwrote:
On Aug 5, 2:57*pm, michel.desang.. .@gmail.com wrote:


On 5 août, 21:17, "Tom P." <padilla.he...@ gmail.comwrote:
On Aug 5, 2:09*pm, "Peter Duniho" <NpOeStPe...@nn owslpianmk.com>
wrote:
On Tue, 05 Aug 2008 11:49:44 -0700, Tom P. <padilla.he...@ gmail.comwrote:
I'm sorry, I must have misspoke. I don't create a thousand different
brushes, I only create about 6 or 9 different brushes... hundredsof
times. [...]
Right, I finally figured that out. *:) *I might just not have been reading *
carefully enough the first time.
I don't think that caching a dozen or so brushes long-term should be an *
issue, if you decide that's a viable design change. *That's not enough to *
cause any serious problems with resource consumption, I think.
Still, I wouldn't bother until if and when you find an actual performance *
problem. *Just remember to dispose any brushes you create, and you'll *
probably be fine.
Pete
Thanks for the help guys. Pete is right, I should have done this
sooner but I was stuck thinking about something from one direction.
Thanks to Michel for giving me the kick in the head to realize how
simple a short test could be.
Using the following code...
for (long loop = 0; loop 1000000000;loop ++ )
* * * * * * {
* * * * * * * * Rectangle tempRect = new Rectangle(0,0,1 00, 18);
* * * * * * * * tempBrush = new LinearGradientB rush(tempRect,
Color.Blue, Color.Red, 0.01F) ;
* * * * * * * * tempBrush = null;
* * * * * * }
...takes 0.00013344 secs. (timed using the hardware HiRes API timer).
I think I can spare 0.00013344 secs.
Sorry Pete.
Tom P.- Masquer le texte des messages précédents -
- Afficher le texte des messages précédents -
Er... Did you copy/paste from Visual Studio ? Because if you did,
maybe you should try again, changing the ">" into a "<"... and remove
three zeros in your loop, otherwise you'll still be waiting
tomorrow... Prepare to be surprised !
Michel

Nope, taken right out of the VS-IDE and pasted in here. If you want
the entire code I suppose I could paste it here as well.

the HiRes timer uses...
[DllImport("kern el32.dll")]
internal extern static UInt32 QueryPerformanc eCounter(ref Int64
lpPerformanceCo unt);

... to get the timings.

Tom P.- Masquer le texte des messages précédents -

- Afficher le texte des messages précédents -
Yes, I know, I'm trying to tell you that you did a typo in your
loop !! It executes only once ! Come on, allocating one billion
objects can't take a millisecond ! Change :

for (long loop = 0; loop 1000000000;loop ++ )

to :

for (long loop = 0; loop < 1000000000;loop ++ )

...and time again, you'll see what I mean. And maybe that'll change
your mind...

Michel
Aug 5 '08 #28
On 05/08/2008 in message
<26************ *************** *******@p25g200 0hsf.googlegrou ps.comTom P.
wrote:
>Nope, taken right out of the VS-IDE and pasted in here. If you want
the entire code I suppose I could paste it here as well.
I suspect Michel meant:
>for (long loop = 0; loop 1000000000;loop ++ )
that won't loop for long :-)

--
Jeff Gaines Damerham Hampshire UK
"Why is it that when we talk to God we're said to be praying,
but when God talks to us we're schizophrenic?"
Aug 5 '08 #29
On Aug 5, 4:49*pm, michel.desang.. .@gmail.com wrote:
On 5 août, 23:36, "Tom P." <padilla.he...@ gmail.comwrote:
On Aug 5, 2:57*pm, michel.desang.. .@gmail.com wrote:
On 5 août, 21:17, "Tom P." <padilla.he...@ gmail.comwrote:
On Aug 5, 2:09*pm, "Peter Duniho" <NpOeStPe...@nn owslpianmk.com>
wrote:
On Tue, 05 Aug 2008 11:49:44 -0700, Tom P. <padilla.he...@ gmail.comwrote:
I'm sorry, I must have misspoke. I don't create a thousand different
brushes, I only create about 6 or 9 different brushes... hundreds of
times. [...]
Right, I finally figured that out. *:) *I might just not havebeen reading *
carefully enough the first time.
I don't think that caching a dozen or so brushes long-term shouldbe an *
issue, if you decide that's a viable design change. *That's notenough to *
cause any serious problems with resource consumption, I think.
Still, I wouldn't bother until if and when you find an actual performance *
problem. *Just remember to dispose any brushes you create, and you'll *
probably be fine.
Pete
Thanks for the help guys. Pete is right, I should have done this
sooner but I was stuck thinking about something from one direction.
Thanks to Michel for giving me the kick in the head to realize how
simple a short test could be.
Using the following code...
for (long loop = 0; loop 1000000000;loop ++ )
* * * * * * {
* * * * * * * * Rectangle tempRect = new Rectangle(0,0,1 00, 18);
* * * * * * * * tempBrush = new LinearGradientB rush(tempRect,
Color.Blue, Color.Red, 0.01F) ;
* * * * * * * * tempBrush = null;
* * * * * * }
...takes 0.00013344 secs. (timed using the hardware HiRes API timer).
I think I can spare 0.00013344 secs.
Sorry Pete.
Tom P.- Masquer le texte des messages précédents -
- Afficher le texte des messages précédents -
Er... Did you copy/paste from Visual Studio ? Because if you did,
maybe you should try again, changing the ">" into a "<"... and remove
three zeros in your loop, otherwise you'll still be waiting
tomorrow... Prepare to be surprised !
Michel
Nope, taken right out of the VS-IDE and pasted in here. If you want
the entire code I suppose I could paste it here as well.
the HiRes timer uses...
[DllImport("kern el32.dll")]
internal extern static UInt32 QueryPerformanc eCounter(ref Int64
lpPerformanceCo unt);
... to get the timings.
Tom P.- Masquer le texte des messages précédents -
- Afficher le texte des messages précédents -

Yes, I know, I'm trying to tell you that you did a typo in your
loop !! It executes only once ! Come on, allocating one billion
objects can't take a millisecond ! Change :

for (long loop = 0; loop 1000000000;loop ++ )

to :

for (long loop = 0; loop < 1000000000;loop ++ )

...and time again, you'll see what I mean. And maybe that'll change
your mind...

Michel
Don't tell my PM, please.

THIS loop...
tempTimer.Start ();
for (int loop = 0; loop < 1000000; loop++)
{
tempRectangle = new Rectangle(0, 0, 100, 18);
tempBrush = new LinearGradientB rush(tempRectan gle,
Color.Blue, Color.Red, 0.01F);

tempBrush.Dispo se();
}
tempTimer.Stop( );

...takes about 5.5 sec.
A mere 1000 brushes takes about 0.005 sec.

Which brings me to another question... Which is best, object.Dispose( )
or Object = null?

Object = null only takes 4.3 secs but I can never keep straight which
one calls the GC twice or under what circumstances. (I can't keep the
stupid "for" loop straight, what are the odds I get this right?)

Tom P.
Aug 6 '08 #30

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

4
2355
by: Chris Lacey | last post by:
Hi, I'm currently writing a scheduling service which starts a number DotNet executables, each within a new AppDomain, every ten seconds. The guts of the code is as follows: // For each executable in the list of tasks for (int i = 0; i < this.processTasks.Length; i++) {
1
4865
by: Rene | last post by:
I would like to get a reference to a Brush using the color name of the brush. For example, right now if I want a brush with a certain color, I would hard code something like Brushes.PeachPuff, this will get me a PeachPuff brush, but what if my brush depended on a string passed by the user? If all I had was a string with the name "PeachPuff" how can I create Brushes.PeachPuff using the string value? Thank you.
2
43463
by: boxim | last post by:
having a moment, cant you just Brush br = new Brush(Color.Black);??? saying you cant cos it's an abstract class need to get to a brush from a color tia sam martin
5
2286
by: Dennis | last post by:
When I instantiate a Brush resource such as a solidbrush, do I need to dispose the resource when I'm finished or will it automatically be disposed when the function/sub it's used in ends? Thank you for any replies. -- Dennis in Houston
1
3861
by: =?Utf-8?B?UEtsZW1t?= | last post by:
how to serialize a brush object with the XmlSerializer without knowing the brush type?
2
1539
by: Johnny J. | last post by:
I've got an inherited control where I want the user to be able to specify a color property. Using that color, I'm drawing a line private m_UserDefinedColor as Color ..... Dim g as Graphics=this.CreateGraphics Dim myPen as Pen = new Pen(m_UserDefinedColor) g.DrawLine(myPen, X1, Y, X2 - 1, Y)
0
1282
by: steve | last post by:
When drawing with a hatch brush with a statement such as myGraphics.FillPolygon(hatchBrush, polygon.vertices); the hatch brush is always oriented in the same direction. Is there a way of rotating the brush so that I can give it a different orientation for each polygon? I.e. if it was a triangle and it was drawn upright then the brush would appear as normal but if the triangle was drawn upside down the hatch brush pattern would...
0
9645
marktang
by: marktang | last post by:
ONU (Optical Network Unit) is one of the key components for providing high-speed Internet services. Its primary function is to act as an endpoint device located at the user's premises. However, people are often confused as to whether an ONU can Work As a Router. In this blog post, we’ll explore What is ONU, What Is Router, ONU & Router’s main usage, and What is the difference between ONU and Router. Let’s take a closer look ! Part I. Meaning of...
0
9480
by: Hystou | last post by:
Most computers default to English, but sometimes we require a different language, especially when relocating. Forgot to request a specific language before your computer shipped? No problem! You can effortlessly switch the default language on Windows 10 without reinstalling. I'll walk you through it. First, let's disable language synchronization. With a Microsoft account, language settings sync across devices. To prevent any complications,...
0
10151
jinu1996
by: jinu1996 | last post by:
In today's digital age, having a compelling online presence is paramount for businesses aiming to thrive in a competitive landscape. At the heart of this digital strategy lies an intricately woven tapestry of website design and digital marketing. It's not merely about having a website; it's about crafting an immersive digital experience that captivates audiences and drives business growth. The Art of Business Website Design Your website is...
1
10092
by: Hystou | last post by:
Overview: Windows 11 and 10 have less user interface control over operating system update behaviour than previous versions of Windows. In Windows 11 and 10, there is no way to turn off the Windows Update option using the Control Panel or Settings app; it automatically checks for updates and installs any it finds, whether you like it or not. For most users, this new feature is actually very convenient. If you want to control the update process,...
0
9950
tracyyun
by: tracyyun | last post by:
Dear forum friends, With the development of smart home technology, a variety of wireless communication protocols have appeared on the market, such as Zigbee, Z-Wave, Wi-Fi, Bluetooth, etc. Each protocol has its own unique characteristics and advantages, but as a user who is planning to build a smart home system, I am a bit confused by the choice of these technologies. I'm particularly interested in Zigbee because I've heard it does some...
1
7499
isladogs
by: isladogs | last post by:
The next Access Europe User Group meeting will be on Wednesday 1 May 2024 starting at 18:00 UK time (6PM UTC+1) and finishing by 19:30 (7.30PM). In this session, we are pleased to welcome a new presenter, Adolph Dupré who will be discussing some powerful techniques for using class modules. He will explain when you may want to use classes instead of User Defined Types (UDT). For example, to manage the data in unbound forms. Adolph will...
0
6740
by: conductexam | last post by:
I have .net C# application in which I am extracting data from word file and save it in database particularly. To store word all data as it is I am converting the whole word file firstly in HTML and then checking html paragraph one by one. At the time of converting from word file to html my equations which are in the word document file was convert into image. Globals.ThisAddIn.Application.ActiveDocument.Select();...
0
5381
by: TSSRALBI | last post by:
Hello I'm a network technician in training and I need your help. I am currently learning how to create and manage the different types of VPNs and I have a question about LAN-to-LAN VPNs. The last exercise I practiced was to create a LAN-to-LAN VPN between two Pfsense firewalls, by using IPSEC protocols. I succeeded, with both firewalls in the same network. But I'm wondering if it's possible to do the same thing, with 2 Pfsense firewalls...
3
2879
bsmnconsultancy
by: bsmnconsultancy | last post by:
In today's digital era, a well-designed website is crucial for businesses looking to succeed. Whether you're a small business owner or a large corporation in Toronto, having a strong online presence can significantly impact your brand's success. BSMN Consultancy, a leader in Website Development in Toronto offers valuable insights into creating effective websites that not only look great but also perform exceptionally well. In this comprehensive...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.