471,594 Members | 2,038 Online
Bytes | Software Development & Data Engineering Community
Post +

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 471,594 software developers and data experts.

Generics & Hashtables (Performance)

Hello!

Now that generics are introduces with the next version of C#, I was
wondering what kind of performance gains we're going to see, when switching
from e.g. the general hashtable to a hashtable that supports (or implements)
generics?

I haven't tried generics hands-on, but I would assume that once you don't
have to do casting anymore, things could speed up quite a bit.

Any comments?

Thanks in advance!

--
venlig hilsen / with regards
anders borum
--
Nov 16 '05 #1
13 1645
Anders Borum <a@b.dk> wrote:
Now that generics are introduces with the next version of C#, I was
wondering what kind of performance gains we're going to see, when switching
from e.g. the general hashtable to a hashtable that supports (or implements)
generics?

I haven't tried generics hands-on, but I would assume that once you don't
have to do casting anymore, things could speed up quite a bit.


Casting is relatively cheap. What will speed things up significantly is
the lack of boxing if you have (say) a Hashtable mapping byte -> byte,
or an ArrayList of bytes.

--
Jon Skeet - <sk***@pobox.com>
http://www.pobox.com/~skeet
If replying to the group, please do not mail me too
Nov 16 '05 #2
"Jon Skeet [C# MVP]" <sk***@pobox.com> wrote in
news:MP************************@msnews.microsoft.c om...
Anders Borum <a@b.dk> wrote:
Now that generics are introduces with the next version of C#, I was
wondering what kind of performance gains we're going to see, when switching from e.g. the general hashtable to a hashtable that supports (or implements) generics?

I haven't tried generics hands-on, but I would assume that once you don't have to do casting anymore, things could speed up quite a bit.


Casting is relatively cheap. What will speed things up significantly is
the lack of boxing if you have (say) a Hashtable mapping byte -> byte,
or an ArrayList of bytes.


Still, if your application doesn't spend half of it's time in hashtable- and
arraylist-lookups, don't expect any noticeable speed improvement.

Niki
Nov 16 '05 #3

"Jon Skeet [C# MVP]" <sk***@pobox.com> wrote in message
news:MP************************@msnews.microsoft.c om...
Anders Borum <a@b.dk> wrote:
Now that generics are introduces with the next version of C#, I was
wondering what kind of performance gains we're going to see, when switching from e.g. the general hashtable to a hashtable that supports (or implements) generics?

I haven't tried generics hands-on, but I would assume that once you don't have to do casting anymore, things could speed up quite a bit.


Casting is relatively cheap. What will speed things up significantly is
the lack of boxing if you have (say) a Hashtable mapping byte -> byte,
or an ArrayList of bytes.


If I understand things correctly, generics won't solve the misbehavior of
structures in containers. That is, given a list of points with x and y
co-ordinates,

list.Get(i).x = 12;

still creates and modifies a temporary instance of the structure, and does
not modify the instance in the list.
Nov 16 '05 #4
>
If I understand things correctly, generics won't solve the misbehavior of
structures in containers. That is, given a list of points with x and y
co-ordinates,

list.Get(i).x = 12;

still creates and modifies a temporary instance of the structure, and does
not modify the instance in the list.
This isn't a misbehavior, its inherent in what a structure is. Like it or
not, the behavior is correct, your expectations aren't.

Nov 16 '05 #5

"Daniel O'Connell [C# MVP]" <onyxkirx@--NOSPAM--comcast.net> wrote in
message news:OG***************@TK2MSFTNGP10.phx.gbl...

If I understand things correctly, generics won't solve the misbehavior of structures in containers. That is, given a list of points with x and y
co-ordinates,

list.Get(i).x = 12;

still creates and modifies a temporary instance of the structure, and does not modify the instance in the list.


This isn't a misbehavior, its inherent in what a structure is.
Like it or
not, the behavior is correct, your expectations aren't.


It's extremely unintuitive, utterly useless, and a booby-trap for the
unwary. That makes it a misbehavior. So is the fact that casting a
structure to an interface creates a copy of the structure. So are the rules
for resolving overrides of overloaded methods in C#. The more misbehaviors
it contains, the less usable a system is.

All of these are "correct" in the sense that they're documented behavior,
but that's a different subject entirely.
Nov 16 '05 #6

"Mike Schilling" <ms*************@hotmail.com> wrote in message
news:%2****************@TK2MSFTNGP11.phx.gbl...

"Daniel O'Connell [C# MVP]" <onyxkirx@--NOSPAM--comcast.net> wrote in
message news:OG***************@TK2MSFTNGP10.phx.gbl...
>
> If I understand things correctly, generics won't solve the misbehavior of > structures in containers. That is, given a list of points with x and y
> co-ordinates,
>
> list.Get(i).x = 12;
>
> still creates and modifies a temporary instance of the structure, and does > not modify the instance in the list.
This isn't a misbehavior, its inherent in what a structure is.
Like it or
not, the behavior is correct, your expectations aren't.


It's extremely unintuitive, utterly useless, and a booby-trap for the
unwary. That makes it a misbehavior. So is the fact that casting a

I don't know. When I have a type that is *guarenteed* to always be passed by
copy, I would hope that I can understand that there is a difference between
a return value(which is a copy) and a field access(which is not). This is
absolutly the same as *every* other pass by value system I've ever seen.
Beyond that, it isn't useless. Why the hell have structs if they are pass by
reference as well? Your proposal entirely removes structures, and all their
benifits strictly because some people can't grasp what pass by value means.
That is their problem, not an issue with the language.

Do you even begin to understand the ramifications of what you are asking
for? Allowing this behavior would *fundamentally* change the language and
force alot of stupid hacks like cloning the object before returning it
because you can't be sure some yahoo wouldn't change a field . Also, what if
the function is
Point GetPoint()
{
Point p = new Point();
return p;
}
What is supposed to happen? is setting GetPoint().X supposed to assign
something in stack space that no longer exists? How is the user to know when
a structure is a field or in an array and when it is locally allocated in
the given method? How, at that, are we to maintain list rules where you
aren't allowed to modify the list?
The behavior you want is impossible and its really a bad idea to want it,
I'm afraid.
structure to an interface creates a copy of the structure. So are the
rules
for resolving overrides of overloaded methods in C#. The more
misbehaviors
Which rules are you concerned about?
it contains, the less usable a system is.
It stands to reason that the less logical the user is, the less likely he
can use the system as well.
All of these are "correct" in the sense that they're documented behavior,
but that's a different subject entirely. Perhaps, although I don't think the documented behavior is a surprise...what
do you expect the language to be like?

Nov 16 '05 #7

"Daniel O'Connell [C# MVP]" <onyxkirx@--NOSPAM--comcast.net> wrote in
message news:Ok**************@TK2MSFTNGP09.phx.gbl...

"Mike Schilling" <ms*************@hotmail.com> wrote in message
news:%2****************@TK2MSFTNGP11.phx.gbl...

"Daniel O'Connell [C# MVP]" <onyxkirx@--NOSPAM--comcast.net> wrote in
message news:OG***************@TK2MSFTNGP10.phx.gbl...
>
> If I understand things correctly, generics won't solve the misbehavior
of
> structures in containers. That is, given a list of points with x and
y > co-ordinates,
>
> list.Get(i).x = 12;
>
> still creates and modifies a temporary instance of the structure, and

does
> not modify the instance in the list.

This isn't a misbehavior, its inherent in what a structure is.
Like it or
not, the behavior is correct, your expectations aren't.


It's extremely unintuitive, utterly useless, and a booby-trap for the
unwary. That makes it a misbehavior. So is the fact that casting a

I don't know. When I have a type that is *guarenteed* to always be passed

by copy, I would hope that I can understand that there is a difference between a return value(which is a copy) and a field access(which is not). This is
absolutly the same as *every* other pass by value system I've ever seen.
Beyond that, it isn't useless. Why the hell have structs if they are pass by reference as well? Your proposal entirely removes structures, and all their benifits strictly because some people can't grasp what pass by value means. That is their problem, not an issue with the language.
list[i].x = 12;

Does this set list[i] or not? Yes, if list is an array, no if it's an
ArrayList. So one the one hand, there's syntax designed explicitly to mask
the distinction between array and ArrayList, on the other hand they act
entirely differently. Wouldn't you agree that's misleading?

structure to an interface creates a copy of the structure. So are the
rules
for resolving overrides of overloaded methods in C#. The more
misbehaviors
Which rules are you concerned about?


See the thread at http://tinyurl.com/38r2r. This is the same principle: the
rules for overloads are stated precisely and followed faithfully, leading to
unexpected behavior.
it contains, the less usable a system is.


It stands to reason that the less logical the user is, the less likely he
can use the system as well.


Have you ever heard of the principle of least astonishment? One of the
goals of system design is to choose low-level behavior that leads to the
high-level behavior that the user would expect. Every system is logical in
that its behavior arises from its implementation; that's how digital
computers work. A well-designed system can be understood without having to
understand the implementation in detail. Structures in .NET don't obey this
rule.
Nov 16 '05 #8

"Mike Schilling" <ms*************@hotmail.com> wrote in message
news:ef**************@tk2msftngp13.phx.gbl...

"Daniel O'Connell [C# MVP]" <onyxkirx@--NOSPAM--comcast.net> wrote in
message news:Ok**************@TK2MSFTNGP09.phx.gbl...

"Mike Schilling" <ms*************@hotmail.com> wrote in message
news:%2****************@TK2MSFTNGP11.phx.gbl...
>
> "Daniel O'Connell [C# MVP]" <onyxkirx@--NOSPAM--comcast.net> wrote in
> message news:OG***************@TK2MSFTNGP10.phx.gbl...
>> >
>> > If I understand things correctly, generics won't solve the misbehavior > of
>> > structures in containers. That is, given a list of points with x
>> > and y >> > co-ordinates,
>> >
>> > list.Get(i).x = 12;
>> >
>> > still creates and modifies a temporary instance of the structure,
>> > and
> does
>> > not modify the instance in the list.
>>
>> This isn't a misbehavior, its inherent in what a structure is.
>>Like it or
>> not, the behavior is correct, your expectations aren't.
>
> It's extremely unintuitive, utterly useless, and a booby-trap for the
> unwary. That makes it a misbehavior. So is the fact that casting a I don't know. When I have a type that is *guarenteed* to always be passed

by
copy, I would hope that I can understand that there is a difference

between
a return value(which is a copy) and a field access(which is not). This is
absolutly the same as *every* other pass by value system I've ever seen.
Beyond that, it isn't useless. Why the hell have structs if they are pass

by
reference as well? Your proposal entirely removes structures, and all

their
benifits strictly because some people can't grasp what pass by value

means.
That is their problem, not an issue with the language.


list[i].x = 12;

Does this set list[i] or not? Yes, if list is an array, no if it's an
ArrayList. So one the one hand, there's syntax designed explicitly to
mask
the distinction between array and ArrayList, on the other hand they act
entirely differently. Wouldn't you agree that's misleading?


Only in as much as properties and indexers are. This is the same as
virtually every difference between fields and properties, actually. Not
terribly surprising, you are expected to know you are working with an array
or not, period.
The difference is that when you are working with an array, list[i] is a
field reference, if you are working with IList, list[i] is a method call
with a *return value*. There is no technical way to make things the way you
want, the only option would be to make arrays behave like indexers, which
would be self defeating as well, wouldn't it?

Also, you can't pass a property, indexer, or method's return value as a ref
or out parameter. Is that surprising too?

> structure to an interface creates a copy of the structure. So are the
> rules
> for resolving overrides of overloaded methods in C#. The more
> misbehaviors


Which rules are you concerned about?


See the thread at http://tinyurl.com/38r2r. This is the same principle:
the
rules for overloads are stated precisely and followed faithfully, leading
to
unexpected behavior.


Ahh, yes, I recall this now. I agree this isn't a well written piece of the
spec.
> it contains, the less usable a system is.


It stands to reason that the less logical the user is, the less likely he
can use the system as well.


Have you ever heard of the principle of least astonishment? One of the
goals of system design is to choose low-level behavior that leads to the
high-level behavior that the user would expect. Every system is logical
in
that its behavior arises from its implementation; that's how digital
computers work. A well-designed system can be understood without having
to
understand the implementation in detail. Structures in .NET don't obey
this
rule.


Thats a matter of opinion. IMHO, it obeys it quite correctly. I expect value
types to require explicit assignment in any case where a copy would occur,
otherwise things don't work. Least astonishment only works when your metric
for determining what is astonishing is actually correct and realistic. In
this case what you are upset about is entirely inherent to the feature. Its
similar, IMHO, to being upset because
Object o = new Object();
Object y = o;

doesn't create two Objects, just one with multiple references. That too will
confuse people who don't understand the implementation and assume = always
means copy the object. And, now, how many other things could I invent a
scenario where the behaviour is unexpected?
Nov 16 '05 #9

"Daniel O'Connell [C# MVP]" <onyxkirx@--NOSPAM--comcast.net> wrote in
message news:un*************@TK2MSFTNGP11.phx.gbl...

"Mike Schilling" <ms*************@hotmail.com> wrote in message
news:ef**************@tk2msftngp13.phx.gbl...

"Daniel O'Connell [C# MVP]" <onyxkirx@--NOSPAM--comcast.net> wrote in
message news:Ok**************@TK2MSFTNGP09.phx.gbl...

"Mike Schilling" <ms*************@hotmail.com> wrote in message
news:%2****************@TK2MSFTNGP11.phx.gbl...
>
> "Daniel O'Connell [C# MVP]" <onyxkirx@--NOSPAM--comcast.net> wrote in
> message news:OG***************@TK2MSFTNGP10.phx.gbl...
>> >
>> > If I understand things correctly, generics won't solve the misbehavior
> of
>> > structures in containers. That is, given a list of points with x
>> > and

y
>> > co-ordinates,
>> >
>> > list.Get(i).x = 12;
>> >
>> > still creates and modifies a temporary instance of the structure,
>> > and
> does
>> > not modify the instance in the list.
>>
>> This isn't a misbehavior, its inherent in what a structure is.
>>Like it or
>> not, the behavior is correct, your expectations aren't.
>
> It's extremely unintuitive, utterly useless, and a booby-trap for the
> unwary. That makes it a misbehavior. So is the fact that casting a
I don't know. When I have a type that is *guarenteed* to always be passed
by
copy, I would hope that I can understand that there is a difference

between
a return value(which is a copy) and a field access(which is not). This
is absolutly the same as *every* other pass by value system I've ever seen. Beyond that, it isn't useless. Why the hell have structs if they are pass by
reference as well? Your proposal entirely removes structures, and all

their
benifits strictly because some people can't grasp what pass by value

means.
That is their problem, not an issue with the language.


list[i].x = 12;

Does this set list[i] or not? Yes, if list is an array, no if it's an
ArrayList. So one the one hand, there's syntax designed explicitly to
mask
the distinction between array and ArrayList, on the other hand they act
entirely differently. Wouldn't you agree that's misleading?


Only in as much as properties and indexers are. This is the same as
virtually every difference between fields and properties, actually. Not
terribly surprising, you are expected to know you are working with an

array or not, period.
The difference is that when you are working with an array, list[i] is a
field reference, if you are working with IList, list[i] is a method call
with a *return value*. There is no technical way to make things the way you want, the only option would be to make arrays behave like indexers, which
would be self defeating as well, wouldn't it?
That is, if I understand the implementation I'll understand the behavior
too. I agree. If you haven't understood by now why this is a problem,
there's no point my explaining it again.

Which rules are you concerned about?


See the thread at http://tinyurl.com/38r2r. This is the same principle:
the
rules for overloads are stated precisely and followed faithfully, leading to
unexpected behavior.


Ahh, yes, I recall this now. I agree this isn't a well written piece of

the spec.


That is, that it's seriously broken and was clearly not thought through?
Yup.

We're clearly not going to agree on any of this, so I'm out.

Mike

Nov 16 '05 #10
want, the only option would be to make arrays behave like indexers, which
would be self defeating as well, wouldn't it?

That is, if I understand the implementation I'll understand the behavior
too. I agree. If you haven't understood by now why this is a problem,
there's no point my explaining it again.


I see where you problem is, I just think its not a real problem and that
your terminology is pretty blatantly wrong. But, I don't care to continue to
argue this either. Obviously its rather unimportant generally, as no one has
stepped in on either side.

Ahh, yes, I recall this now. I agree this isn't a well written piece of

the
spec.


That is, that it's seriously broken and was clearly not thought through?
Yup.

We're clearly not going to agree on any of this, so I'm out.


Bye!
Nov 16 '05 #11
Hello!
Allowing this behavior would *fundamentally* change the language and
force alot of stupid hacks like cloning the object before returning it

(..)

Not sure this is in context of what you're saying, but what are the options
to cloning?

I would like to know how you would keep an internal cache (as per previous
in topic), populated with instances (reference types), then try to control
what the user is doing with the objects as they are passed from the cache
(for instance, setting a property affects the cached object)?

Aside from cloning the object, and handing out a version that lives with the
users domain (so that he is actually seeing the same object), what are the
real alternatives?

--
venlig hilsen / with regards
anders borum
--
Nov 16 '05 #12
Hello!

I'm glad to see such activity on topic, lots of interesting readings as
usual.
Still, if your application doesn't spend half of it's time in hashtable- and arraylist-lookups, don't expect any noticeable speed improvement.


The reason I'm asking is that I'm developing an API where caching is handled
internally in a set of hashtables (to simplify things quite dramatically).
These objects are accessed very frequently (thousands of lookups each
second).

I have complete control over which types of objects are placed in the
hashtables, and thus considered generics relevant. I'm not looking for
considerable improvements, but had the impression that it could make a
difference.

--
venlig hilsen / with regards
anders borum
--
Nov 16 '05 #13

"Anders Borum" <a@b.dk> wrote in message
news:eM**************@TK2MSFTNGP10.phx.gbl...
Hello!
Allowing this behavior would *fundamentally* change the language and
force alot of stupid hacks like cloning the object before returning it (..)

Not sure this is in context of what you're saying, but what are the
options
to cloning?

I would like to know how you would keep an internal cache (as per previous
in topic), populated with instances (reference types), then try to control
what the user is doing with the objects as they are passed from the cache
(for instance, setting a property affects the cached object)?

Aside from cloning the object, and handing out a version that lives with
the
users domain (so that he is actually seeing the same object), what are the
real alternatives?


Outside of a proxy, there arne't any if I understand you.
--
venlig hilsen / with regards
anders borum
--

Nov 16 '05 #14

This discussion thread is closed

Replies have been disabled for this discussion.

Similar topics

18 posts views Thread by Maxim Kazitov | last post: by
6 posts views Thread by Michael Schollmeyer | last post: by
10 posts views Thread by Ruediger Klaehn | last post: by
9 posts views Thread by sloan | last post: by
reply views Thread by John Smith | last post: by
reply views Thread by Jake McCool | last post: by
8 posts views Thread by Tony Johansson | last post: by
reply views Thread by XIAOLAOHU | last post: by
reply views Thread by Anwar ali | last post: by

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.