PC Review


Reply
Thread Tools Rate Thread

collection class performance seems SLOOOWWWWWW

 
 
ian.smith@bmtcordah.com
Guest
Posts: n/a
 
      20th Jun 2006
I have a small sellection of code here. When the "button1_Click" is
called the performance is quite poor (~ 0.5 sec). Only thing is I am
not really doing anything!! In C++ the same thing takes ~ 0 seconds to
execute!!. The List<Pumpicle> is faster than ArrayList and I convert
the List to an array before access. It just seems to be something like
unboxing the doubles out of the Pumpicle class. Any ideas??

PumpicleContainer pc = null;

private void Form1_Load(object sender, EventArgs e)
{
pc = new PumpicleContainer();

for (int i = 0; i < 10000; i++)
{
pc.Add(new Pumpicle());
}

pc.ToArray();
}

public class DaublePoint
{
public double m_x;
public double m_y;
public double m_z;
};

public class Pumpicle
{
public DaublePoint m_pos;
public double m_mass;

public Pumpicle()
{
m_pos = new DaublePoint();
}
};

class PumpicleContainer
{
public List<Pumpicle> m_pList = new List<Pumpicle>();

Pumpicle[] m_arr = null;

public void Add(Pumpicle p)
{
m_pList.Add(p);
}

public void ToArray()
{
m_arr = m_pList.ToArray();
}

public Pumpicle GetParticle(int i)
{
return m_arr[i];
}
}

private void button1_Click(object sender, EventArgs e)
{
pc.ToArray();

long start = System.DateTime.Now.Ticks;

int np = 0;
for (int idx = 0; idx < 20; idx++)
{
np += 22;
for (int i = -33; i <= 33; i++)
{
for (int j = -33; j <= 33; j++)
{
for (int l = 0; l < 5; l++)
{
for (int ps = 0; ps < np; ps++)
{
Pumpicle p = pc.GetParticle(ps);

DaublePoint pt = p.m_pos;
double x = pt.m_x;
double y = pt.m_y;
double z = pt.m_z;
}
}
}
}
}

long end = System.DateTime.Now.Ticks;

MessageBox.Show("Finished = " + ((end - start) / 1e7));
}

 
Reply With Quote
 
 
 
 
jeremiah johnson
Guest
Posts: n/a
 
      21st Jun 2006
I notice a couple of things.

you're doing 448900 iterations through those nested for loops (and I'm
not even counting the ps < np loop - who knows what that adds on).

You're measuring time incorrectly. instead of
System.DateTime.Now.Ticks, use System.DateTime.Now in both places. Then
subtract them and arrive at a TimeSpan, then call elapsedMillis() on the
TimeSpan object. The way you measure it now, if you happen to cross a
second boundary, you could wind up with very inconsistent execution times.

DateTime then = System.DateTime.Now;
// your loop here.
DateTime now = System.DateTime.Now;
TimeSpan ts = now - then;
Console.WriteLine(ts.TotalMilliseconds);

Jeremiah

(E-Mail Removed) wrote:
> I have a small sellection of code here. When the "button1_Click" is
> called the performance is quite poor (~ 0.5 sec). Only thing is I am
> not really doing anything!! In C++ the same thing takes ~ 0 seconds to
> execute!!. The List<Pumpicle> is faster than ArrayList and I convert
> the List to an array before access. It just seems to be something like
> unboxing the doubles out of the Pumpicle class. Any ideas??
>
> PumpicleContainer pc = null;
>
> private void Form1_Load(object sender, EventArgs e)
> {
> pc = new PumpicleContainer();
>
> for (int i = 0; i < 10000; i++)
> {
> pc.Add(new Pumpicle());
> }
>
> pc.ToArray();
> }
>
> public class DaublePoint
> {
> public double m_x;
> public double m_y;
> public double m_z;
> };
>
> public class Pumpicle
> {
> public DaublePoint m_pos;
> public double m_mass;
>
> public Pumpicle()
> {
> m_pos = new DaublePoint();
> }
> };
>
> class PumpicleContainer
> {
> public List<Pumpicle> m_pList = new List<Pumpicle>();
>
> Pumpicle[] m_arr = null;
>
> public void Add(Pumpicle p)
> {
> m_pList.Add(p);
> }
>
> public void ToArray()
> {
> m_arr = m_pList.ToArray();
> }
>
> public Pumpicle GetParticle(int i)
> {
> return m_arr[i];
> }
> }
>
> private void button1_Click(object sender, EventArgs e)
> {
> pc.ToArray();
>
> long start = System.DateTime.Now.Ticks;
>
> int np = 0;
> for (int idx = 0; idx < 20; idx++)
> {
> np += 22;
> for (int i = -33; i <= 33; i++)
> {
> for (int j = -33; j <= 33; j++)
> {
> for (int l = 0; l < 5; l++)
> {
> for (int ps = 0; ps < np; ps++)
> {
> Pumpicle p = pc.GetParticle(ps);
>
> DaublePoint pt = p.m_pos;
> double x = pt.m_x;
> double y = pt.m_y;
> double z = pt.m_z;
> }
> }
> }
> }
> }
>
> long end = System.DateTime.Now.Ticks;
>
> MessageBox.Show("Finished = " + ((end - start) / 1e7));
> }
>

 
Reply With Quote
 
Bruce Wood
Guest
Posts: n/a
 
      21st Jun 2006

(E-Mail Removed) wrote:
> Only thing is I am not really doing anything!! In C++ the same thing takes ~ 0 seconds to execute!!.


> int np = 0;
> for (int idx = 0; idx < 20; idx++)
> {
> np += 22;
> for (int i = -33; i <= 33; i++)
> {
> for (int j = -33; j <= 33; j++)
> {
> for (int l = 0; l < 5; l++)
> {
> for (int ps = 0; ps < np; ps++)
> {
> Pumpicle p = pc.GetParticle(ps);
>
> DaublePoint pt = p.m_pos;
> double x = pt.m_x;
> double y = pt.m_y;
> double z = pt.m_z;
> }
> }
> }
> }
> }


Be very, very careful about comparisons like this! You are right: the
code isn't doing anything useful. The C++ compiler may be smart enough
to detect that only the outermost loop has any lasting effect: it
changes np. If the compiler is clever enough to know that
pc.GetParticle(ps) has no side-effects, then it may simply eliminate
the inner loops altogether.

Are you sure that in C++ pc.GetParticle is being called the number of
times you expect? Or is it never called at all?

Then again it may simply be that the C++ compiler produces much better
code. However, you can't tell just from doing a benchmark like this
without further checks.

 
Reply With Quote
 
Joanna Carter [TeamB]
Guest
Posts: n/a
 
      21st Jun 2006
<(E-Mail Removed)> a écrit dans le message de news:
(E-Mail Removed)...

|I have a small sellection of code here. When the "button1_Click" is
| called the performance is quite poor (~ 0.5 sec). Only thing is I am
| not really doing anything!! In C++ the same thing takes ~ 0 seconds to
| execute!!. The List<Pumpicle> is faster than ArrayList and I convert
| the List to an array before access. It just seems to be something like
| unboxing the doubles out of the Pumpicle class. Any ideas??

1. Why convert the list to an array before access ? this takes time !!

2. You are not unboxing anything as you are holding doubles and retrieving
doubles.

Instead of your PumpicleContainer class, just use a List<Pumpicle> as it is
without any wrapper class and see if that makes any difference.

Joanna

--
Joanna Carter [TeamB]
Consultant Software Engineer


 
Reply With Quote
 
ian.smith@bmtcordah.com
Guest
Posts: n/a
 
      22nd Jun 2006

> 1. Why convert the list to an array before access ? this takes time !!


It takes time but nothing compared to accessing the List directly
several times over. The array is faster to access than the list.

> 2. You are not unboxing anything as you are holding doubles and retrieving
> doubles.
>


You are right I was suggesting something like that going on.

> Instead of your PumpicleContainer class, just use a List<Pumpicle> as it is
> without any wrapper class and see if that makes any difference.


I have made the ToArray function return the array and then the code
uses that. That is faster (thanks). Again Array is faster than List<>
which is way faster than ArrayList

 
Reply With Quote
 
ian.smith@bmtcordah.com
Guest
Posts: n/a
 
      22nd Jun 2006
> Be very, very careful about comparisons like this! You are right:
the
> code isn't doing anything useful. The C++ compiler may be smart enough
> to detect that only the outermost loop has any lasting effect: it
> changes np. If the compiler is clever enough to know that
> pc.GetParticle(ps) has no side-effects, then it may simply eliminate
> the inner loops altogether.


The problem is actually I am comparing C# with FORTRAN. I have ported
the code over from FORTRAN and then proceded to tell my colleges how
much faster the C# would be. Then I ran the code go my ass smacked!!
The bottleneck was in this code loop. Remember that FORTRAN was used by
dinosuars, how can it be faster than C#!!!

 
Reply With Quote
 
ian.smith@bmtcordah.com
Guest
Posts: n/a
 
      22nd Jun 2006
> DateTime then = System.DateTime.Now;
> // your loop here.
> DateTime now = System.DateTime.Now;
> TimeSpan ts = now - then;
> Console.WriteLine(ts.TotalMilliseconds);


With the world cup on I would say "back of the net". Completly correct
:-). The timing was meant to be figurative but it pays to be precise.
Thanks.

 
Reply With Quote
 
Jon Skeet [C# MVP]
Guest
Posts: n/a
 
      22nd Jun 2006
<(E-Mail Removed)> wrote:
> > 1. Why convert the list to an array before access ? this takes time !!

>
> It takes time but nothing compared to accessing the List directly
> several times over. The array is faster to access than the list.


If you rearranged your loops to do what it currently the inner loop as
the outer loop, you'd be accessing the list much, much, much less
often, however. Of course, it's difficult to know whether or not that's
feasible when your code doesn't do anything useful with idx, i, j, or l
though.

--
Jon Skeet - <(E-Mail Removed)>
http://www.pobox.com/~skeet Blog: http://www.msmvps.com/jon.skeet
If replying to the group, please do not mail me too
 
Reply With Quote
 
Bruce Wood
Guest
Posts: n/a
 
      23rd Jun 2006
(E-Mail Removed) wrote:
> > Be very, very careful about comparisons like this! You are right:

> the
> > code isn't doing anything useful. The C++ compiler may be smart enough
> > to detect that only the outermost loop has any lasting effect: it
> > changes np. If the compiler is clever enough to know that
> > pc.GetParticle(ps) has no side-effects, then it may simply eliminate
> > the inner loops altogether.

>
> The problem is actually I am comparing C# with FORTRAN. I have ported
> the code over from FORTRAN and then proceded to tell my colleges how
> much faster the C# would be. Then I ran the code go my ass smacked!!
> The bottleneck was in this code loop. Remember that FORTRAN was used by
> dinosuars, how can it be faster than C#!!!


It wouldn't surprise me at all that FORTRAN / COBOL / C might be
_faster_ than C#. If anyone claimed to me that C# is _faster_ then I
would immediately be suspicious.

C# comes with tremendous advances in the ability to organize code (O-O
/ visual designers, etc), advances in security, interoperability with
databases, etc.... but speed? No, I don't think so.

If we're writing a sophisticated multi-cultural / multi-language
WinForms application that calls Web Services or reads from a database,
and I'm using C# and you're using C, I'm sure that I could _write_ the
code much, much faster than you could, but would my code _run_ faster
in the end? Probably after my two weeks of coding and your ten months
of coding, your code would probably run faster, but that's not the
"why" of using C# in that scenario, is it?

 
Reply With Quote
 
ian.smith@bmtcordah.com
Guest
Posts: n/a
 
      24th Jun 2006
> If you rearranged your loops

Thanks, but that wasn't the point of the exercise. It is to demonstrate
how seemingly inefficient C# can be at times especially concerning the
collection classes.

 
Reply With Quote
 
 
 
Reply

Thread Tools
Rate This Thread
Rate This Thread:

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
Adding class object to collection repeats same object through collection? Erazmus Microsoft Excel Programming 2 17th Sep 2007 04:35 AM
Collection problems (create Collection object, add data to collection, bind collection to datagrid) Øyvind Isaksen Microsoft ASP .NET 1 18th May 2007 10:24 AM
Can't get collection to save when using collection of custom class as property of control in VS 2005 J.Edwards Microsoft Dot NET Compact Framework 0 10th Jan 2006 04:44 AM
Class X Creates Collection of Instances of Class Y. Y's need info from X Jim Frazer Microsoft C# .NET 3 16th Jun 2004 09:17 AM
RaiseEvent from a class contained in a 2nd class collection? Andrew Microsoft Excel Programming 2 6th Jan 2004 04:22 PM


Features
 

Advertising
 

Newsgroups
 


All times are GMT +1. The time now is 06:49 PM.