JavaRush /Blog Java /Random-PL /Rzucanie typów pierwotnych. Rzutowanie na krótki i bajt
Георгий
Poziom 22
Санкт-Петербург

Rzucanie typów pierwotnych. Rzutowanie na krótki i bajt

Opublikowano w grupie Random-PL
Rzucanie typów pierwotnych.  Rzutowanie int na krótki i bajt - 1Dlaczego jest tak, że jeśli rzutujesz niektóre wartości typu intna typ shortlub byte, wyniki są nieoczekiwane? Dowiedzmy Się!
int i = 450;
byte b = (byte)i;
System.out.println(b);
Wynik na ekranie:

-62
Nieoczekiwanie istnieje na to logiczne wyjaśnienie, a ponadto tę czynność można wykonać własnymi rękami. Aby to zrobić, musimy przekonwertować 450 z postaci dziesiętnej na binarną:

450/2.    0
225/2.    1
112/2.    0
56/2.     0
28/2.     0
14/2.     0
7/2.      1
3/2.      1
1/2.      1
W prawej kolumnie liczby zapisujemy resztę z dzielenia przez 2, a pod samą liczbą zapisujemy wynik dzielenia naszej liczby przez dwa, jeśli reszta wynosi 0. Jeśli reszta wynosi 1, to poniżej piszemy część całkowita z dzielenia przez dwa. ( Kalkulator online z wyjaśnieniem obliczeń ). W rezultacie otrzymujemy to w systemie liczb binarnych 450 = 11100 0010. Dowolny numer typu intzajmuje 4 bajty czyli 32 bity, gdzie każdy bit to 0 lub 1. W naszym przypadku zajętych jest tylko 9 bitów i w zasadzie nasz int i = 450w systemie binarnym wygląda tak:

0000_0000_0000_0000_0000_0001_1100_0010
Naszą zmienną chcemy zapisać do zmiennej typu byte, ale numer typu bytezajmuje 1 bajt (jak wynika z nazwy tego typu) lub 8 bitów. Dlatego dodatkowe bity po lewej stronie są po prostu odrzucane i ostatecznie otrzymujemy:

1100 0010
Wpisz zakres wartości byte: -128 do 127. Każda liczba zajmuje 8 bitów, a bit znajdujący się najbardziej na lewo od każdej liczby jest bitem znaku. Dla wszystkich liczb dodatnich jest ona równa 0, dla wszystkich liczb ujemnych jest równa 1. Nie ma co się spieszyć z przeliczaniem otrzymanego powyżej wyniku na system 10-ty, gdyż otrzymaliśmy dodatkowy kod na żądany numer, a nie bezpośredni. Najbardziej lewy bit okazał się równy 1, dlatego nasza liczba jest ujemna, a dla liczb ujemnych kody bezpośrednie i odwrotne nie pokrywają się, w przeciwieństwie do kodów dodatnich. Gdyby bit znaku był równy 0, moglibyśmy natychmiast przekonwertować liczbę na system dziesiętny i otrzymać: 66. Ale bit znaku jest ujemny, więc najpierw musimy przekonwertować dodatkowy kod na kod bezpośredni i dodać minus podpisz się pod odpowiedzią. Dla przejrzystości i szkolenia spróbujmy najpierw uzyskać dodatkowy kod jakiejś liczby, na przykład -15. Aby to zrobić, w bezpośrednim kodzie jego dodatniej reprezentacji (liczba 15) należy zamienić wszystkie zera na jedynki i odwrotnie (uzyskać kod odwrotny, zwany także odwrotnością), a następnie dodać jedynkę do wyniku. W systemie dziesiętnym 15 = 0000 1111; Kod odwrotny (zamień wszystkie 0 na 1 i odwrotnie) = 1111 0000; Dodatkowy kod (dodaj):

1 1 1 1 0 0 0 0
0 0 0 0 0 0 0 1
1 1 1 1 0 0 0 1
Kod dodatkowy dla liczby -15: 1111 0001; Świetnie.Teraz analogicznie do powyższego przykładu musimy zamienić nasz dodatkowy kod na kod bezpośredni, przypominam, że jest on równy 1100 0010.
  1. Odejmij jeden i uzyskaj kod odwrotny. Wygodnie jest to zrobić, wpisać w odpowiedzi dodatkowy kod i zobaczyć, do czego trzeba go dodać, aby otrzymać taki dodatkowy kod. Zaczynamy od cyfry znajdującej się najbardziej na prawo i sprawdzamy: do czego musimy dodać 1, aby otrzymać 0? Do 1 dostajemy 10, 0 idzie w odpowiedzi, a 1 przechodzi do następnej cyfry. Następnie, co należy dodać do 0, aby otrzymać jeden. Jeden, ale skoro mamy jedynkę z poprzedniej cyfry, to w odpowiedzi piszemy 0. Następnie, aby otrzymać 0, co powinniśmy dodać do 0? Oczywiście 0. A więc jeszcze 4 razy. I zostały jeszcze 2 ostatnie cyfry, gdzie trzeba dodać coś do 0, żeby otrzymać 1. Oczywiście w obu przypadkach trzeba dodać 1. Razem:

    
    1 1 0 0 0 0 0 1
    0 0 0 0 0 0 0 1
    1 1 0 0 0 0 1 0
  2. Najtrudniejsza część już za nami! Otrzymaliśmy kod odwrotny (odwrotny) i jedyne, co musimy zrobić, to uzyskać kod bezpośredni. Zamieniamy wszystkie 0 na 1 i odwrotnie:

    1100 0001- kod odwrotny;

    0011 1110 - bezpośredni kod naszego numeru, a raczej jego pozytywna reprezentacja;

  3. Zamień na system dziesiętny ( Kalkulator online z wyjaśnieniem obliczeń ):

    0011 1110 = 0∙2^7+0∙2^6+1∙2^5+1∙2^4+1∙2^3+1∙2^2+1∙2^1+0∙2^0 = 0+0+32+16+8+4+2+0 = 62;

    Pozostaje tylko dodać minus do liczby i naszą odpowiedź:-62.

W ten sam sposób liczby typu są konwertowane shortna typ int:
int i = 10_000_000;
short s = (short)i;
System.out.println(s); // -27008
  1. 10 000 000 w 10. systemie liczbowym = 0000 0000 1001 1000 1001 0110 1000 0000w 2. systemie liczbowym.

    W Javie numer typu intzajmuje 4 bajty, a shortnumer typu 2 bajty, czyli 16 bitów, więc odcinamy lewą stronę do 16 cyfr:

  2. 1001 0110 1000 0000. Najbardziej lewy bit (bit najbardziej znaczący, zwany także bitem znaku) okazał się równy 1. Oznacza to, że mamy dodatkowy kod na liczbę ujemną, więc przechodzimy do następnego punktu.
  3. Przetłumaczmy to na kod odwrotny:

    
    1 0 0 1 0 1 1 0 0 1 1 1 1 1 1 1
    0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 1
    1 0 0 1 0 1 1 0 1 0 0 0 0 0 0 0

    Kod powrotu: 1001 0110 0111 1111;

  4. Odwracamy i otrzymujemy bezpośredni kod: 0110 1001 1000 0000.

  5. Konwertujemy na system liczb binarnych i otrzymujemy pozytywną reprezentację naszej liczby:

    1∙2^14+1∙2^13+1∙2^11+1∙2^8+1∙2^7 = 16384+8192+2048+256+128 = 27008.
  6. Dodaj minus i uzyskaj odpowiedź:-27008

Rzucanie typów pierwotnych.  Rzutowanie int na krótki i bajt - 2Link do kalkulatora online kodów forward, reverse i uzupełniających. Również na tej stronie pod kalkulatorem jest trochę teorii na temat kodu odwrotnego i dopełniającego.
Komentarze
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION