By using this site, you agree to our updated Privacy Policy and our Terms of Use. Manage your Cookies Settings.
440,352 Members | 1,593 Online
Bytes IT Community
+ Ask a Question
Need help? Post your question and get tips & solutions from a community of 440,352 IT Pros & Developers. It's quick & easy.

A simple question about foreach and datatypes

P: n/a
Hello!

Why does not this cause a compile error because a ulong has never been
implicitly convertible to byte?

ulong[] vektor = {100000,200000,300000};
foreach(byte b in vektor)
{
Console.WriteLine("i={0}", b);
}

If I have these statements below then I get a compile error.
But it's almost the same as above. Is a bug perhaps?

ulong a = 1;
byte b;
b = a; // Here a ulong is not implicitly convertible to a byte so we get a
compile error which is correct

//Tony

Oct 19 '07 #1
Share this Question
Share on Google+
7 Replies


P: n/a
Your foreach loop instructions are basically translated by the C# compiler
into a bunch of other instructions that are understood by the CLR.

One of the instructions that is emitted on your behalf is an instruction to
convert ulong to a byte without throwing an overflow error.

If you are not ok with this behavior you can change it in code by adding the
check using word:

checked
{
ulong[] vektor = { 100000, 200000, 300000 };
foreach (byte b in vektor)
{
Console.WriteLine("i={0}", b);
}
}
"Tony Johansson" <jo*****************@telia.comwrote in message
news:KC*****************@newsb.telia.net...
Hello!

Why does not this cause a compile error because a ulong has never been
implicitly convertible to byte?

ulong[] vektor = {100000,200000,300000};
foreach(byte b in vektor)
{
Console.WriteLine("i={0}", b);
}

If I have these statements below then I get a compile error.
But it's almost the same as above. Is a bug perhaps?

ulong a = 1;
byte b;
b = a; // Here a ulong is not implicitly convertible to a byte so we get a
compile error which is correct

//Tony

Oct 19 '07 #2

P: n/a
Hello!

Why does not this generate a compile error?
That's my question.
What is the reason for the compiler to accept this type of conversion.

//Tony

"Rene" <a@b.comskrev i meddelandet
news:el**************@TK2MSFTNGP06.phx.gbl...
Your foreach loop instructions are basically translated by the C# compiler
into a bunch of other instructions that are understood by the CLR.

One of the instructions that is emitted on your behalf is an instruction
to convert ulong to a byte without throwing an overflow error.

If you are not ok with this behavior you can change it in code by adding
the check using word:

checked
{
ulong[] vektor = { 100000, 200000, 300000 };
foreach (byte b in vektor)
{
Console.WriteLine("i={0}", b);
}
}
"Tony Johansson" <jo*****************@telia.comwrote in message
news:KC*****************@newsb.telia.net...
>Hello!

Why does not this cause a compile error because a ulong has never been
implicitly convertible to byte?

ulong[] vektor = {100000,200000,300000};
foreach(byte b in vektor)
{
Console.WriteLine("i={0}", b);
}

If I have these statements below then I get a compile error.
But it's almost the same as above. Is a bug perhaps?

ulong a = 1;
byte b;
b = a; // Here a ulong is not implicitly convertible to a byte so we get
a
compile error which is correct

//Tony


Oct 19 '07 #3

P: n/a
As was explained before, the foreach loop is translated into this
(something like it):

using (IEnumerator enumerator = vektor.GetEnumerator())
{
while (enumerator.MoveNext())
{
byte b = (byte)enumerator.Current;
Console.WriteLine("i={0}", b);
}
}

There is an explicit (not implicit) cast that will succeed in your
case. However, the error, if there is one, will only occur at runtime.

The reason it succeeds in the generated code and not your code is that
the compiler puts some extra care into it to make sure it does
compile. Your example does not provide an explicit cast, while the
generated version does.

While I cannot send you the exact generated code (it is in MSIL), just
know that it does something similar to my example.

Oct 19 '07 #4

P: n/a
Why does not this generate a compile error?
That's my question.
For the same reason code below does not generate an error.

ulong a = 1;
byte b;
b = Convert.ToByte(a);

There is nothing wrong with code above, in that snippet, you are stating
that you want to convert a ulong to a byte and not to trhow an error if the
conversion overflows. why would the compiler throw a compile error here??

Like I said before, internally, the C# compiler is taking your foreach code
and creating code that the CLR can understand, **this icludes** generating
code that is doing the **convertion without trhouwing an error**, something
similar to the example avobe.

What is the reason for the compiler to accept this type of conversion.
Ah, because when you do a foreach loop internally you are calling the
GetEnumerator() function wich in turn return an IEnumerator that in turn
returns objects as it collection member, so there is no way to do a compile
time check because the compiler does not whats inside the object. You can
check the definition of the IEnumerator for more info.

If you want to loop throw an array and have the compile time check then do a
"for" loop.

ulong[] vektor = { 100000, 200000, 300000 };
for (int i = 0; i < vektor.Length; i++)
{
byte b = vektor[i];
Console.WriteLine("i={0}", b);
}


>
//Tony

"Rene" <a@b.comskrev i meddelandet
news:el**************@TK2MSFTNGP06.phx.gbl...
>Your foreach loop instructions are basically translated by the C#
compiler into a bunch of other instructions that are understood by the
CLR.

One of the instructions that is emitted on your behalf is an instruction
to convert ulong to a byte without throwing an overflow error.

If you are not ok with this behavior you can change it in code by adding
the check using word:

checked
{
ulong[] vektor = { 100000, 200000, 300000 };
foreach (byte b in vektor)
{
Console.WriteLine("i={0}", b);
}
}
"Tony Johansson" <jo*****************@telia.comwrote in message
news:KC*****************@newsb.telia.net...
>>Hello!

Why does not this cause a compile error because a ulong has never been
implicitly convertible to byte?

ulong[] vektor = {100000,200000,300000};
foreach(byte b in vektor)
{
Console.WriteLine("i={0}", b);
}

If I have these statements below then I get a compile error.
But it's almost the same as above. Is a bug perhaps?

ulong a = 1;
byte b;
b = a; // Here a ulong is not implicitly convertible to a byte so we get
a
compile error which is correct

//Tony



Oct 19 '07 #5

P: n/a
Hello!!

I understand what you mean but I would be more happy if this would cause a
compile error.
I think that the compiler is doing a bad job hiding an important error when
using byte for an ulong.

There is certainly a good reson for why the compiler is doing a thing that
may seems bad.
//Tony

<je**********@gmail.comskrev i meddelandet
news:11**********************@q5g2000prf.googlegro ups.com...
As was explained before, the foreach loop is translated into this
(something like it):

using (IEnumerator enumerator = vektor.GetEnumerator())
{
while (enumerator.MoveNext())
{
byte b = (byte)enumerator.Current;
Console.WriteLine("i={0}", b);
}
}

There is an explicit (not implicit) cast that will succeed in your
case. However, the error, if there is one, will only occur at runtime.

The reason it succeeds in the generated code and not your code is that
the compiler puts some extra care into it to make sure it does
compile. Your example does not provide an explicit cast, while the
generated version does.

While I cannot send you the exact generated code (it is in MSIL), just
know that it does something similar to my example.

Oct 19 '07 #6

P: n/a
Hello!

Good explained thanks!

//Tony

"Rene" <a@b.comskrev i meddelandet
news:u1**************@TK2MSFTNGP05.phx.gbl...
>Why does not this generate a compile error?
That's my question.

For the same reason code below does not generate an error.

ulong a = 1;
byte b;
b = Convert.ToByte(a);

There is nothing wrong with code above, in that snippet, you are stating
that you want to convert a ulong to a byte and not to trhow an error if
the conversion overflows. why would the compiler throw a compile error
here??

Like I said before, internally, the C# compiler is taking your foreach
code and creating code that the CLR can understand, **this icludes**
generating code that is doing the **convertion without trhouwing an
error**, something similar to the example avobe.

>What is the reason for the compiler to accept this type of conversion.
Ah, because when you do a foreach loop internally you are calling the
GetEnumerator() function wich in turn return an IEnumerator that in turn
returns objects as it collection member, so there is no way to do a
compile time check because the compiler does not whats inside the object.
You can check the definition of the IEnumerator for more info.

If you want to loop throw an array and have the compile time check then do
a "for" loop.

ulong[] vektor = { 100000, 200000, 300000 };
for (int i = 0; i < vektor.Length; i++)
{
byte b = vektor[i];
Console.WriteLine("i={0}", b);
}


>>
//Tony

"Rene" <a@b.comskrev i meddelandet
news:el**************@TK2MSFTNGP06.phx.gbl...
>>Your foreach loop instructions are basically translated by the C#
compiler into a bunch of other instructions that are understood by the
CLR.

One of the instructions that is emitted on your behalf is an instruction
to convert ulong to a byte without throwing an overflow error.

If you are not ok with this behavior you can change it in code by adding
the check using word:

checked
{
ulong[] vektor = { 100000, 200000, 300000 };
foreach (byte b in vektor)
{
Console.WriteLine("i={0}", b);
}
}
"Tony Johansson" <jo*****************@telia.comwrote in message
news:KC*****************@newsb.telia.net...
Hello!

Why does not this cause a compile error because a ulong has never been
implicitly convertible to byte?

ulong[] vektor = {100000,200000,300000};
foreach(byte b in vektor)
{
Console.WriteLine("i={0}", b);
}

If I have these statements below then I get a compile error.
But it's almost the same as above. Is a bug perhaps?

ulong a = 1;
byte b;
b = a; // Here a ulong is not implicitly convertible to a byte so we
get a
compile error which is correct

//Tony





Oct 19 '07 #7

P: n/a
JT
On Oct 19, 3:42 pm, "Tony Johansson" <johansson.anders...@telia.com>
wrote:
Hello!

Good explained thanks!

//Tony

"Rene" <a...@b.comskrev i meddelandetnews:u1**************@TK2MSFTNGP05.phx. gbl...
Why does not this generate a compile error?
That's my question.
For the same reason code below does not generate an error.
ulong a = 1;
byte b;
b = Convert.ToByte(a);
There is nothing wrong with code above, in that snippet, you are stating
that you want to convert a ulong to a byte and not to trhow an error if
the conversion overflows. why would the compiler throw a compile error
here??
Like I said before, internally, the C# compiler is taking your foreach
code and creating code that the CLR can understand, **this icludes**
generating code that is doing the **convertion without trhouwing an
error**, something similar to the example avobe.
What is the reason for the compiler to accept this type of conversion.
Ah, because when you do a foreach loop internally you are calling the
GetEnumerator() function wich in turn return an IEnumerator that in turn
returns objects as it collection member, so there is no way to do a
compile time check because the compiler does not whats inside the object.
You can check the definition of the IEnumerator for more info.
If you want to loop throw an array and have the compile time check then do
a "for" loop.
ulong[] vektor = { 100000, 200000, 300000 };
for (int i = 0; i < vektor.Length; i++)
{
byte b = vektor[i];
Console.WriteLine("i={0}", b);
}
//Tony
"Rene" <a...@b.comskrev i meddelandet
news:el**************@TK2MSFTNGP06.phx.gbl...
Your foreach loop instructions are basically translated by the C#
compiler into a bunch of other instructions that are understood by the
CLR.
>One of the instructions that is emitted on your behalf is an instruction
to convert ulong to a byte without throwing an overflow error.
>If you are not ok with this behavior you can change it in code by adding
the check using word:
>checked
{
ulong[] vektor = { 100000, 200000, 300000 };
foreach (byte b in vektor)
{
Console.WriteLine("i={0}", b);
}
}
>"Tony Johansson" <johansson.anders...@telia.comwrote in message
news:KC*****************@newsb.telia.net...
Hello!
>>Why does not this cause a compile error because a ulong has never been
implicitly convertible to byte?
>>ulong[] vektor = {100000,200000,300000};
foreach(byte b in vektor)
{
Console.WriteLine("i={0}", b);
}
>>If I have these statements below then I get a compile error.
But it's almost the same as above. Is a bug perhaps?
>>ulong a = 1;
byte b;
b = a; // Here a ulong is not implicitly convertible to a byte so we
get a
compile error which is correct
>>//Tony- Hide quoted text -

- Show quoted text -
I was looking at the VS options (Tools... Options...). I found a
setting for VB in Projects and Solutions, Option Strict, that when
checked will require explicit conversions, but I didn't see anything
for C#. However, I certainly wouldn't advise anyone to use VB because
of that. :^>

Since I haven't changed project Build settings from the defaults, I
don't know if this would be caught or not, but you could probably go
into the Project Properties, the Build tab, and change settings to
give you more control over your error reporting. You might try
unchecking the Optimize code checkbox. Make sure Warning Level is set
to the highest number. Make sure the Suppress warnings text box is
clear. Under Treat warnings as errors, check the Specific warnings
radio button and specify a warning that you would want elevated to an
error. I don't know what that would be, but I think the Help files
might give you that.

JT

Oct 20 '07 #8

This discussion thread is closed

Replies have been disabled for this discussion.