# What is the input range of (x >> 8) before overflow kicks in?

Discussion in 'C++' started by Mr. Ken, Jan 22, 2007.

1. ### Mr. KenGuest

I am running such segment of codes, but errors kick in after maybe
absolute of x above 10^6.

What is the theoritical bound of x before I get errors?

double x;
int y;

x = ......;

y = ((int)x) >> 8;

Thanks.

Mr. Ken, Jan 22, 2007

2. ### Ondra HolubGuest

Mr. Ken napsal:
> I am running such segment of codes, but errors kick in after maybe
> absolute of x above 10^6.
>
> What is the theoritical bound of x before I get errors?
>
>
>
> double x;
> int y;
>
> x = ......;
>
> y = ((int)x) >> 8;
>
> Thanks.

#include <limits>

if (x <= std::numeric_limits<int>::max() && x >=
std::numeric_limits<int>::min())
{
// x typecasted to int will fit into int
}

Ondra Holub, Jan 22, 2007

3. ### Mr. KenGuest

"Ondra Holub" <> wrote in message
news:...
>
> Mr. Ken napsal:
> > I am running such segment of codes, but errors kick in after maybe
> > absolute of x above 10^6.
> >
> > What is the theoritical bound of x before I get errors?
> >
> >
> >
> > double x;
> > int y;
> >
> > x = ......;
> >
> > y = ((int)x) >> 8;
> >
> > Thanks.

>
> #include <limits>
>
> if (x <= std::numeric_limits<int>::max() && x >=
> std::numeric_limits<int>::min())
> {
> // x typecasted to int will fit into int
> }
>

Thank you but it doesn't solve my problem since sometimes x is not shifted.

I am using y = (int)(x/256.0), which is nearly correct.

However I liked the ">>" due to its readability.

Mr. Ken, Jan 22, 2007
4. ### Kai-Uwe BuxGuest

Mr. Ken wrote:

>
> "Ondra Holub" <> wrote in message
> news:...
>>
>> Mr. Ken napsal:
>> > I am running such segment of codes, but errors kick in after maybe
>> > absolute of x above 10^6.
>> >
>> > What is the theoritical bound of x before I get errors?
>> >
>> >
>> >
>> > double x;
>> > int y;
>> >
>> > x = ......;
>> >
>> > y = ((int)x) >> 8;
>> >
>> > Thanks.

>>
>> #include <limits>
>>
>> if (x <= std::numeric_limits<int>::max() && x >=
>> std::numeric_limits<int>::min())
>> {
>> // x typecasted to int will fit into int
>> }
>>

>
> Thank you but it doesn't solve my problem since sometimes x is not
> shifted.

If it does not solve your problem, then you did not explain you problem
correctly: you asked about the range of error-free behavior for the line

y = ( (int)x ) >> 8;

This line has well-define behavior if and only if the double x can be
converted to an int without overflow or underflow. The test suggested by
Ondra Holup ensures exactly that. What you do with the int-casted double
afterwards is immaterial.

> I am using y = (int)(x/256.0), which is nearly correct.
>
> However I liked the ">>" due to its readability.

Maybe you should fill us in on the precise requirements. If you tell us the
specs for the transformation x -> y, someone might be able to suggest code
that is more than "nearly" correct.

Best

Kai-Uwe Bux

Kai-Uwe Bux, Jan 22, 2007
5. ### Ondra HolubGuest

Mr. Ken napsal:
> "Ondra Holub" <> wrote in message
> news:...
> >
> > Mr. Ken napsal:
> > > I am running such segment of codes, but errors kick in after maybe
> > > absolute of x above 10^6.
> > >
> > > What is the theoritical bound of x before I get errors?
> > >
> > >
> > >
> > > double x;
> > > int y;
> > >
> > > x = ......;
> > >
> > > y = ((int)x) >> 8;
> > >
> > > Thanks.

> >
> > #include <limits>
> >
> > if (x <= std::numeric_limits<int>::max() && x >=
> > std::numeric_limits<int>::min())
> > {
> > // x typecasted to int will fit into int
> > }
> >

>
> Thank you but it doesn't solve my problem since sometimes x is not shifted.
>
> I am using y = (int)(x/256.0), which is nearly correct.
>
> However I liked the ">>" due to its readability.

Hi. I am not sure what you exactly need. (int)(x/256.0) is not the same
as ((int)x)/256; Former first divides x with 256 and then typecasts it
to int. Latter variant first typecasts x to int and then divides it
with 256.

So you can still check the result of x / 256.0 whether it fits to int.

BTW: x >> 8 is IMO not more readable than x / 256 and I bet every
compiler is able to change x / 256 to bit shift automatically (of
course when x is integer value).

Ondra Holub, Jan 22, 2007
6. ### peter kochGuest

Kai-Uwe Bux wrote:
[snip]
> [...]you asked about the range of error-free behavior for the line
>

(assuming double x)
> y = ( (int)x ) >> 8;
>
> This line has well-define behavior if and only if the double x can be
> converted to an int without overflow or underflow.

[snip]

Are you sure? So far as I know shifts of integer types only have well
defined behaviour when the left argument is non-negative.

/Peter

peter koch, Jan 22, 2007
7. ### Kai-Uwe BuxGuest

peter koch wrote:

>
> Kai-Uwe Bux wrote:
> [snip]
>> [...]you asked about the range of error-free behavior for the line
>>

> (assuming double x)
>> y = ( (int)x ) >> 8;
>>
>> This line has well-define behavior if and only if the double x can be
>> converted to an int without overflow or underflow.

> [snip]
>
> Are you sure? So far as I know shifts of integer types only have well
> defined behaviour when the left argument is non-negative.

Ah, I should have said "not undefined" instead of "well-defined". You are
right: for negative integers, the resulting value is implementation defined
[5.8/3]. However, I would consider that still error-free behavior.

Best

Kai-Uwe Bux

Kai-Uwe Bux, Jan 22, 2007
8. ### Sylvester HespGuest

"Ondra Holub" <> wrote in message
news:...
>
> BTW: x >> 8 is IMO not more readable than x / 256 and I bet every
> compiler is able to change x / 256 to bit shift automatically (of
> course when x is integer value).
>

Of course when x is an _unsigned_ integer. -1 / 256 == 0, but on most
implementations, -1 >> 8 == -1 due to the use of the arithmetic shift right
on a signed int (and an implementation using a logical shift left can't even
use that instruction for dividing signed integers ). This leads to the
need for extra (perhaps relatively expensive, of course depending on the
platform) checks, therefore a regular divide instruction rather than a shift
can be chosen to "optimize" the expression.

- Sylvester

Sylvester Hesp, Jan 22, 2007
9. ### Mr. KenGuest

"Kai-Uwe Bux" <> wrote in message
news:ep1uj0\$54l\$...
> Mr. Ken wrote:
>
> >
> > "Ondra Holub" <> wrote in message
> > news:...
> >>
> >> Mr. Ken napsal:
> >> > I am running such segment of codes, but errors kick in after maybe
> >> > absolute of x above 10^6.
> >> >
> >> > What is the theoritical bound of x before I get errors?
> >> >
> >> >
> >> >
> >> > double x;
> >> > int y;
> >> >
> >> > x = ......;
> >> >
> >> > y = ((int)x) >> 8;
> >> >
> >> > Thanks.
> >>
> >> #include <limits>
> >>
> >> if (x <= std::numeric_limits<int>::max() && x >=
> >> std::numeric_limits<int>::min())
> >> {
> >> // x typecasted to int will fit into int
> >> }
> >>

> >
> > Thank you but it doesn't solve my problem since sometimes x is not
> > shifted.

>
> If it does not solve your problem, then you did not explain you problem
> correctly: you asked about the range of error-free behavior for the line
>
> y = ( (int)x ) >> 8;
>
> This line has well-define behavior if and only if the double x can be
> converted to an int without overflow or underflow. The test suggested by
> Ondra Holup ensures exactly that. What you do with the int-casted double
> afterwards is immaterial.
>
>
> > I am using y = (int)(x/256.0), which is nearly correct.
> >
> > However I liked the ">>" due to its readability.

>
> Maybe you should fill us in on the precise requirements. If you tell us

the
> specs for the transformation x -> y, someone might be able to suggest code
> that is more than "nearly" correct.
>
>
> Best
>
> Kai-Uwe Bux

Basically the C++ will be converted to hardware with logic gates. I will use
maybe 35-bits
for integers in 2's complement formats.

In C++ sims, I would define everything in "double" and x may end up be

z = sign * (0.0, 1.0, ...8191.0);
x = z * pow(2.0, 21);

y = ((int)x) >> 8.

y will be scaled down version of x. And ">>" is the usual operator we use in
the company.

I would like to know the exact z when y becomes erronous.

Mr. Ken, Jan 23, 2007