C++ - ridiculous long long range

2019-05-28 18:48发布

问题:

Me and my friend have just encountered a very weird issue with long long range. So basically, my computer has a 64bit processor but a 32 bit system on it. He has both 32 bit OS and CPU.

First, we printfed sizeof(long long). For both of us that was 8.

Then we did this:

long long blah = 1;

printf ("%lld\n", blah<<40);

For me this returns 1099511627776 (which is the correct result). For him it is 0.

How is that possible? We both have the same sizeofs.

Thanks in advance.

EDIT: I compiled and ran it under Win7 with Code Blocks 12.11. He uses Win XP and the same version of CB.

EDIT2: Source codes as requested:

#include <cstdio>

int main()
{
    long long blah = 1;

    printf ("%lld\n", blah<<40);

    return 0;
}

and

#include <cstdio>

int main()
{
    printf ("%d", sizeof(long long));

    return 0;
}

回答1:

I would guess that you and your friends are linking to different versions of the infamous MSVCRT.DLL or possibly some other library.

From the Code::Blocks FAQ:

Q: What Code::Blocks is not?

A: Code::Blocks is not a compiler, nor a linker. Release packages of Code::Blocks may include a compiler suite (MinGW/GCC), if not provided by the target platform already. However, this is provided "as-is" and not developed/maintained by the Code::Blocks development team.

So the statement "I compiled and ran it under Win7 with Code Blocks 12.11" isn't strictly true; you cannot compile with something that isn't a compiler.

Figure out what compiler you two are actually using (see, above: it is not "Code Blocks") and what library.



回答2:

Could be one of two problems: either the printing system cannot cope with long long or the shift operator does not work over 32 bits. Try this

#include <cstdio>
int main()
{
   union
   {
      long long one;

      // Intel based systems are back to front
      struct {
         long lo;
         long hi;
      } two;
   } xxx;

   xxx.one = 1LL;
   xxx.one = xxx.one << 40;
   printf ("%016llx %08x %08x\n", xxx.one, xxx.two.hi, xxx.two.lo);
   return 0;
}

If the first number is all zeros but one of the other two isn't, then it is the printf that cannot cope. If all the numbers are zeros, then the shift operator isn't defined for 64 bits.