Mit használ az 1ll a hosszú hosszú állításban l = (int) a * 1ll * (int) b; a C / C ++ nyelven?


Legjobb válasz

Először egy gripe: A C és a C ++ két különböző nyelv. Az alábbi válasz történetesen mindkettőre vonatkozik, de a válasz néha eltér a nyelvek között. És mindkét nyelven a c/c++ kifejezés viselkedése undefined.

Ez egy ostoba módja egy típusú promóció megszerzésének Ne feledje, hogy a részletekben szereplő példa világosabban fogalmaz:

int a, b;

long long l = a * 1ll * b;

Amint az OP megjegyzi, a 1ll egy long long egész számot literálnak nyilvánít.

Ez a jelenlét itt a kódban elősegíti a teljes szaporítást long long felé a szokásos számtani konverziók révén, különösen a egész promóciók.

A kifejezés ((a * 1ll) * b) néven értelmezhető. Az első szorzás csak a a értéket adja vissza, mint long long. Ezután a második szorzás long long -re is frissül.

Ugyanezt a hatást érhette el explicit cast-tal:

int a, b;

long long l = (long long)a * b;

Kicsit inkább gépel, de csak kissé. A második megfogalmazás minden bizonnyal egyértelműbb, legalábbis számomra.

Ilyen módon is tehet:

long long l = a;

l *= b;

De ez megint butasággá válik.

Amiért miért kell népszerűsítened? Ha elég nagy értéke van, akkor a szorzás túlcsordulhat. A long long fájlba történő promócióval garantálja, hogy nem fog.

Tegyük fel, hogy 32 bites int és 64- bit long long és a 2-es komplementer reprezentáció. A legnagyobb termék, amelyet kaphat, -2 ^ {31} \ -szerese -2 ^ {31} = 2 ^ {62}. Ez alatta van a legnagyobb pozitív értéknek, amelyet képviselhet, 2 ^ {63} – 1, így garantáltan nem fog túlcsordulni.

Válasz

a és b int int * int -> int (mindez a 32 bites int tartományban van ie -2147483648 int 2147483647) . “. 2147483647 * 2 = -2 és nem 4294967294 hozzárendelés operátor asszociativitással rendelkezik jobbról balra , azaz a kifejezésben: hosszú hosszú l = az a * b; a * b értéket először int * int-> int számoljuk ki, ha a = 2147483647 és b = 2 a * b -> – 2 és nem 4294967294, akkor most l = -2 -2 hosszúra konvertálódik és l-ben tárolódik

Vélemény, hozzászólás?

Az email címet nem tesszük közzé. A kötelező mezőket * karakterrel jelöltük