473,218 Members | 1,824 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

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

Strange behaviour of long long and unsigned int

Hi everybody,
please, can someone explain me this behaviour.

I have the following piece of code:

long long ll;
unsigned int i = 2;
ll = -1 * i;
printf("%lld\n", ll);

Why this prints 4294967294 instead of -2?
Thanks in advance
Luke

Mar 8 '06 #1
9 3894
Just type cast -1 to long long.

ll = (long long)-1 * i;

Thats it.

Mar 8 '06 #2
luke wrote:
Hi everybody,
please, can someone explain me this behaviour.

I have the following piece of code:

long long ll;
unsigned int i = 2;
ll = -1 * i;
printf("%lld\n", ll);

Why this prints 4294967294 instead of -2?


http://c-faq.com/expr/intoverflow1.html
Mar 8 '06 #3
"luke" <lr*****@yahoo.com> writes:
I have the following piece of code:

long long ll;
unsigned int i = 2;
ll = -1 * i;
printf("%lld\n", ll);

Why this prints 4294967294 instead of -2?


In
ll = -1 * i;
the expression -1 is of type int, and i is of type unsigned int, so
the -1 is converted to unsigned int before the multiplication.
Converting -1 to unsigned int yields UINT_MAX, which happens to be
4294967295 in your implementation. Multiplying 4294967295 by 2 wraps
around (because it's unsigned arithmetic), yielding 4294967294.

--
Keith Thompson (The_Other_Keith) ks***@mib.org <http://www.ghoti.net/~kst>
San Diego Supercomputer Center <*> <http://users.sdsc.edu/~kst>
We must do something. This is something. Therefore, we must do this.
Mar 8 '06 #4
Thanks.
Where can I find the rules for arithmetic conversions?
I found this rules (taken from an ANSI C manual):

"First, if the corresponding real type of either operand is long
double, the other
operand is converted, without change of type domain, to a type whose
corresponding real type is long double.
Otherwise, if the corresponding real type of either operand is double,
the other
operand is converted, without change of type domain, to a type whose
corresponding real type is double.
Otherwise, if the corresponding real type of either operand is float,
the other
operand is converted, without change of type domain, to a type whose
corresponding real type is float.
Otherwise, the integer promotions are performed on both operands. Then
the
following rules are applied to the promoted operands:
If both operands have the same type, then no further conversion is
needed.
Otherwise, if both operands have signed integer types or both have
unsigned
integer types, the operand with the type of lesser integer conversion
rank is
converted to the type of the operand with greater rank.
Otherwise, if the operand that has unsigned integer type has rank
greater or
equal to the rank of the type of the other operand, then the operand
with
signed integer type is converted to the type of the operand with
unsigned
integer type.
Otherwise, if the type of the operand with signed integer type can
represent
all of the values of the type of the operand with unsigned integer
type, then
the operand with unsigned integer type is converted to the type of the
operand with signed integer type.
Otherwise, both operands are converted to the unsigned integer type
corresponding to the type of the operand with signed integer type."

Are this rules good or maybe can you suggest anything better?
Thanks

Keith Thompson wrote:
"luke" <lr*****@yahoo.com> writes:
I have the following piece of code:

long long ll;
unsigned int i = 2;
ll = -1 * i;
printf("%lld\n", ll);

Why this prints 4294967294 instead of -2?


In
ll = -1 * i;
the expression -1 is of type int, and i is of type unsigned int, so
the -1 is converted to unsigned int before the multiplication.
Converting -1 to unsigned int yields UINT_MAX, which happens to be
4294967295 in your implementation. Multiplying 4294967295 by 2 wraps
around (because it's unsigned arithmetic), yielding 4294967294.


Mar 8 '06 #5
luke wrote:
Thanks.
Where can I find the rules for arithmetic conversions?
The ISO (and ANSI) C Standard.
I found this rules (taken from an ANSI C manual):

"First, if the corresponding real type of either operand is long
double, the other ....
Are this rules good or maybe can you suggest anything better?


They are correct and useful, assuming you understand what is meant by
integer rank.

--
Thad
Mar 9 '06 #6
Mmmh, I think rank is what is returned by sizeof() but I'm not sure
about this.
Can you explain me what rank really means?
Thanks
Luke

Thad Smith wrote:
luke wrote:
Thanks.
Where can I find the rules for arithmetic conversions?


The ISO (and ANSI) C Standard.
I found this rules (taken from an ANSI C manual):

"First, if the corresponding real type of either operand is long
double, the other

...
Are this rules good or maybe can you suggest anything better?


They are correct and useful, assuming you understand what is meant by
integer rank.

--
Thad


Mar 9 '06 #7
In another ANSI C manual I found the following rules, which are
different from the previous ones.
Which one are good then??

1.

If either operand is long double, the other operand is converted
to long double.
2.

If either operand is double, the other operand is converted to
double.
3.

If either operand is float, the other operand is converted to
float.
4.

Integral promotions are performed on both operands, and then the
rules listed below are followed. These rules are a strict extension of
the ANSI "Usual Arithmetic Conversions" rule (Section 3.2.1.5). This
extension ensures that integral expressions will involve long long only
if one of the operands is of type long long. For ANSI conforming
compilation, the integral promotion rule is as defined in Section
3.2.1.1 of the Standard. For non-ANSI compilation, the unsigned
preserving promotion rule is used.
1.

If either operand is unsigned long long, the other operand
is converted to unsigned long long,
2.

otherwise, if one operand is long long, the other operand
is converted to long long,
3.

otherwise, if either operand is unsigned long int, the
other operand is converted to unsigned long int,
4.

otherwise, if one operand is long int, and the other is
unsigned
int, and long int can represent all the values of an
unsigned
int, then the unsigned int is converted to a long int. (If
one operand is long int, and the other is unsigned int, and long int
can NOT represent all the values of an unsigned int, then both operands
are converted to unsigned long int.)
5.

If either operand is long int, the other operand is
converted to long int.
6.

If either operand is unsigned int, the other operand is
converted to unsigned int.
7.

Otherwise, both operands have type int.
Regards

Thad Smith wrote:
Are this rules good or maybe can you suggest anything better?


They are correct and useful, assuming you understand what is meant by
integer rank.

--
Thad


Mar 9 '06 #8
"luke" <lr*****@yahoo.com> wrote:

[ Please do not top-post. Please do snip. Thank you. ]
Mmmh, I think rank is what is returned by sizeof() but I'm not sure
about this.
No, but it's a related concept. sizeof returns the actual storage size
any type or object takes in bytes of memory; rank is a (relative, and
non-measurable) indicator of the ideal mathematical size of an integer
type.
Can you explain me what rank really means?


It is defined precisely in paragraph 6.3.1.1 of the Standard, but
basically, it's an indicator - not even a number - of how "large" a type
is, in the sense of what it can and must be able to contain. For
example:
- a signed type and its corresponding unsigned type have the same rank
- no signed integer types have the same rank, even if they look the same
in all respects
- a signed type which can hold larger numbers has higher rank than one
which can hold smaller numbers
- even if, say, INT_MAX == LONG_MAX, the rank of long is higher than
that of int, and similar for the other default types
- _Bool has the lowest rank of all
and so on.

The significance of this rank is that when integer types need to be
compared to one another, types with lower rank are generally converted
to types with higher rank.

Richard
Mar 9 '06 #9
Groovy hepcat luke was jivin' on 9 Mar 2006 01:49:02 -0800 in
comp.lang.c.
Re: Strange behaviour of long long and unsigned int's a cool scene!
Dig it!
In another ANSI C manual I found the following rules, which are
different from the previous ones.
No they're not. They're the same. They're just stated differently.
They amount to the same thing.
Which one are good then??


Both. But the set of rules you've quoted here (which I've snipped)
lacks a rule for when both operands have the same type. But otherwise
it's fine.

--

Dig the even newer still, yet more improved, sig!

http://alphalink.com.au/~phaywood/
"Ain't I'm a dog?" - Ronny Self, Ain't I'm a Dog, written by G. Sherry & W. Walker.
I know it's not "technically correct" English; but since when was rock & roll "technically correct"?
Mar 12 '06 #10

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

Similar topics

20
by: Markus Sandheide | last post by:
Hello! Execute these lines: int x = 1; x = x > 2345678901; You will get: x == 1 with Borland C++ Builder
6
by: Edd Dawson | last post by:
Hi. I have a strange problem involving the passing of command line arguments to a C program I'm writing. I tried posting this in comp.programming yesterday but someone kindly suggested that I'd...
5
by: cpptutor2000 | last post by:
I am compiling and running the following code snippet on a Linux box - I am really puzzled by the answers. Could someone please tell me what might be wrong? void test(){ int m = 0; int n = 0;...
10
by: bear | last post by:
hi all, I have a program whose speed is so strange to me. It is maily used to calculate a output image so from four images s0,s1,s2,s3 where so=(s0-s2)^2+ (s1-s3)^2. I compile it with gcc (no...
7
by: Netocrat | last post by:
The code at the bottom illustrates the nature of a situation discussed on comp.lang.asm.x86. Basically an unsigned integer is being used as a negative index in a loop, and it works as though the...
31
by: gamehack | last post by:
Hi all, I've been testing out a small function and surprisingly it does not work okay. Here's the full code listing: #include "stdlib.h" #include "stdio.h" char* escaped_byte_cstr_ref(char...
8
by: FBM | last post by:
Hi there, I am puzzled with the behavior of my code.. I am working on a networking stuff, and debugging with eclipse (GNU gdb 6.6-debian).. The problem I am experiencing is the following: ...
46
by: suresh | last post by:
Hi, For this code snippet, I get the following output, which I am unable to understand. (2^31 = 2147483648) cout<< -2147483648 << endl; cout << numeric_limits<int>::min() <<',' <<...
14
by: leptone | last post by:
Dear all, I am programming a PLC with an 80188 processor, hence I am using an old version of Borland C++ (3.10). While doing the job, I've encountered strange behaviours and I've isolated the...
1
isladogs
by: isladogs | last post by:
The next online meeting of the Access Europe User Group will be on Wednesday 6 Dec 2023 starting at 18:00 UK time (6PM UTC) and finishing at about 19:15 (7.15PM). In this month's session, Mike...
0
by: veera ravala | last post by:
ServiceNow is a powerful cloud-based platform that offers a wide range of services to help organizations manage their workflows, operations, and IT services more efficiently. At its core, ServiceNow...
0
by: VivesProcSPL | last post by:
Obviously, one of the original purposes of SQL is to make data query processing easy. The language uses many English-like terms and syntax in an effort to make it easy to learn, particularly for...
3
isladogs
by: isladogs | last post by:
The next Access Europe meeting will be on Wednesday 3 Jan 2024 starting at 18:00 UK time (6PM UTC) and finishing at about 19:15 (7.15PM). For other local times, please check World Time Buddy In...
0
by: jianzs | last post by:
Introduction Cloud-native applications are conventionally identified as those designed and nurtured on cloud infrastructure. Such applications, rooted in cloud technologies, skillfully benefit from...
2
by: jimatqsi | last post by:
The boss wants the word "CONFIDENTIAL" overlaying certain reports. He wants it large, slanted across the page, on every page, very light gray, outlined letters, not block letters. I thought Word Art...
0
by: fareedcanada | last post by:
Hello I am trying to split number on their count. suppose i have 121314151617 (12cnt) then number should be split like 12,13,14,15,16,17 and if 11314151617 (11cnt) then should be split like...
0
Git
by: egorbl4 | last post by:
Скачал я git, хотел начать настройку, а там вылезло вот это Что это? Что мне с этим делать? ...
0
by: MeoLessi9 | last post by:
I have VirtualBox installed on Windows 11 and now I would like to install Kali on a virtual machine. However, on the official website, I see two options: "Installer images" and "Virtual machines"....

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.