Commit a08f4e86 by Patryk Czarnik

zmienne i typy

parent 1bb3885e
package p03_zmienne_i_typy;
public class A_Zmienne {
// zmienne z poziomu klasy - tzw. "pola"
// statyczna - jeden egzemplarz dla klasy
static int statyczna;
// "instancyjna" - oddzilenie dla każdego obiektu
int instancyjna;
public static void main(String[] args) {
// W Javie zmienne muszą zadeklarowane
// System.out.println(x);
// x = 100;
// System.out.println(x);
// Sama deklaracja zmienej:
int x;
// Java nie inicjalizuje automatycznie zmiennych lokalnych.
// Niezainicjowanych zmiennych nie wolno czytać (błąd kompilacji)
// System.out.println(x);
x = 150;
System.out.println("x = " + x);
// zmienne z poziomu klasy SĄ automatycznie inicjowane na 0, null lub false
System.out.println("statyczna = " + statyczna);
int y;
if(x > 100) {
y = 500;
System.out.println("y = " + y);
}
// tutaj kompilator "nie ma pewności", że y jest zainicjowany
// System.out.println("y = " + y);
if(x > 100) {
y = 500;
} else {
y = 600;
}
System.out.println("y = " + y);
}
}
package p03_zmienne_i_typy;
import java.time.LocalDateTime;
public class B_Typy {
public static void main(String[] args) {
// 8 typów prostych:
// liczby calkowite: byte, short, int, long
byte b = 100;
short s = 1000;
int i = 23;
long l = 333;
System.out.println(b * s * i * l);
// 2 typy dla liczb z ułamkiem. liczby "zmiennopozycyjne" / "zmiennoprzeconkowe" (floating point)
float f = 3.14F;
double d = 123.456;
System.out.println(f * d);
System.out.println();
// char - pojedynczy znak, ale patrząc technicznie, to jest liczba 16-bitowa, która może być kodem znaku
char c = 'A';
System.out.println(c);
System.out.println(c+1); // kodem litery A jest 65
c++;
// teraz jednak "przesuwamy znak" o jedną pozycję do przodu
System.out.println(c);
boolean warunek = true;
System.out.println(warunek);
warunek = f < 3;
System.out.println(warunek);
// przy okazji dwa sposoby umieszczania egzotycznych znaków w napisach:
if(warunek) {
System.out.println("\u03C0 jest małe");
} else {
System.out.println("π jest duże");
}
System.out.println();
// Typy obiektowe: klasa, interfejs, enum, rekord oraz tablice
// Sama Java definiuje ich kilka tysięcy, a programiści mogą tworzyć własne
String napis = "Ala ma kota";
System.out.println(napis);
System.out.println(napis.toUpperCase());
LocalDateTime czas = LocalDateTime.now();
System.out.println(czas);
System.out.println("Godzina " + czas.getHour() + " minut " + czas.getMinute());
// itd, jest tego bardzo dużo
}
}
package p03_zmienne_i_typy;
public class BityIBajty {
/* Program wypisuje wartość zmiennej typu byte oraz jej zapis w pamięci w postaci ciągu 8 bitów, zwiększając w pętli wartość o 1.
* Widać zjawisko integer overflow: wartość +127 przechodzi w wartość -128.
* Dla zmiennych typu short, int, long jest analogicznie; różnica jest w długości ciągu bitów (16, 32 i 64) i zakresie liczb.
*/
public static void main(String[] args) {
System.out.println("Zwiększanie bajta:");
byte b = 0;
for(int i = 0; i <= 512; i++) {
String bity = Integer.toBinaryString(Byte.toUnsignedInt(b));
bity = String.format("%8s", bity);
bity = bity.replace(' ', '0');
System.out.printf("%4d : %s%n", b, bity);
b++;
}
}
}
package p03_zmienne_i_typy;
public class Ciekawostki {
public static void main(String[] args) {
int x = 5, y = 1000000000;
int z = x * y;
System.out.println(z);
System.out.println(5 * 1000000000);
System.out.println(5L * 1000000000);
System.out.println(3 * 1000000000);
// Gdy wynik obliczenia nie mieści się w zakresie dla danego typu (int lub long)
// dochodzi do "integer overflow". W Javie nie powoduje to błędu (w sensie wyjątku),
// po prostu wychodzi "przekręcony" wynik.
System.out.println();
double a = 3.0, b = 1.2;
System.out.println(a * b);
System.out.println(3 * 1.2);
double oczekiwany = 3.6;
if(a * b == oczekiwany) {
System.out.println("OK");
} else {
System.out.println("Nie OK");
System.out.println("różnica: " + (oczekiwany - a * b));
}
System.out.println();
// Liczby zmiennoprzecinkowe (w Javie: float i double) działają w przybliżeniu.
// W pamięci są zapisany w systemie dwójkowym, a nie dziesiętnym, więc zaokrąglenia nastepują w zapisie binarnym liczby, co utrudnia zrozumienie.
// Praktyczny morał: double nie używa się do liczenia pieniędzy.
// Lepszą alternatywą jest wyspecjalizowana klasa BigDecimal.
// Liczba całkowita zapisana w kodzie zaczynając od cyfry 0, jest w systemie ósemkowym.
int n = 0321; // = 3*64 + 2*8 + 1*1
System.out.println(n);
System.out.println(0321);
//NK int m = 098;
System.out.println();
// Od Javy 7 między cyframi można wpisywać znaki _ , które nie zmieniają wartości
int i = 123_456_789;
System.out.println(i);
int j = 123____4___5;
System.out.println(j);
}
}
package p03_zmienne_i_typy;
public class Dzielenie {
public static void main(String[] args) {
double d = 1.25;
int n = 5;
// Uwaga na kolejność działań gdy miesza się inty i double
// Tutaj: int dzielony porzez int - wynik obcinany do liczby całkowitej
System.out.println(n / 3 * d);
// dzielenie na doublach
System.out.println(n * d / 3);
System.out.println(1.0 * n / 3 * d);
System.out.println((double)n / 3 * d);
System.out.println();
System.out.println("Dzielenie całkowite i reszta z dzielenia:");
for(int i = -10; i <= 10; i++) {
System.out.printf("%3d / 3 = %2d %3d %% 3 = %2d\n", i, i / 3, i, i % 3);
}
}
}
package p03_zmienne_i_typy;
public class LiteralyLiczbowe {
public static void main(String[] args) {
int x;
x = 123; // format dziesiętny
System.out.println(x);
x = 0123; // system ósemkowy
//NK x = 08; // cyfry od 0 do 7
System.out.println(x);
x = 0x100; // system szesnastkowy
System.out.println(x);
x = 0x7F;
System.out.println(x);
// system dwójkowy - od Javy 7
x = 0b1101;
System.out.println(x);
// odstępy pomiędzy cyframi - od Javy 7
x = 2_000_000;
System.out.println(x);
//NK long l = 4000000000; // wartość nie mieszcząca się w int
long l = 4000000000L; // OK
// int _1000 = 1313;
// x = _1000; // odwołanie do zmiennej :)
// x = 1000_;
x = 10______00; // po prostu tysiąc
// dopuszczalne są tylko pomiędzy cyframi.
// nie na początku, nie na końcu, nie obok kropki ani obok litery typu i wykładnika
x = 0x0F_FF_80_00;
x = 0b0011_0101;
System.out.println(x); // 1000
double dd = 10__00;
dd = 3.14; // literał liczbowy z częścią ułamkową jest typu double (a nie float)
dd = 1_00.0__0;
//dd = 100._9;
//dd = 100_.9;
dd = 100.99d;
//dd = 100.99_f;
// x = 0x_FF;
// NK x = 1L; // L na końcu oznacza typ long (może być duże lub małe)
l = 1L;
l = 1; // inta można wpisać na zmienną long
System.out.println();
float f = 12; // int na float - OK
// f = 3.14;
// literał z ułamkiem jest typu double, a double nie można wpisać na float
f = 3.14F;
f = 1.0f;
f = 3f;
f = 1.13e2F;
f = (float)3.14; // kompiluje się, ale niezalecane, bo można zgubić precyzję
System.out.println(f);
double d = 3.14;
// NK f = d;
// na końcu double'a też można podać info o typie: D albo d
d = 4.44d;
d = 4.445D;
// liczba w notacji dziesiętnej razy 10 do podanej potęgi
d = 1.25e3;
System.out.println(d);
d = 4.44e-3;
System.out.println(d);
System.out.println();
// liczba w notacji szestastkowej razy 2 do podanej potęgi - tak to jest przechowywane wewnętrznie!
d = 0x3p2; // 12
System.out.println(d);
d = 0x0.2p0; // 2/16 = 1/8 = 0.125
System.out.println(d);
d = 0x1p-3;
System.out.println(d);
}
}
package p03_zmienne_i_typy;
import java.util.Locale;
import java.util.Scanner;
public class MnozenieFloat {
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
scanner.useLocale(Locale.US);
System.out.print("Podaj dwie liczby dziesiętne: ");
double x = scanner.nextDouble();
double y = scanner.nextDouble();
double wynik = x * y;
System.out.println("wynik = " + wynik);
System.out.printf("wynik : %.2f\n", wynik);
System.out.printf(Locale.US, "wynik : %.2f\n", wynik);
}
}
package p03_zmienne_i_typy;
import java.util.Scanner;
public class MnozenieInt {
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
System.out.print("Podaj dwie liczby całkowite: ");
int x = scanner.nextInt();
int y = scanner.nextInt();
int wynik1 = x * y;
System.out.println("wynik1 = " + wynik1);
try {
int wynik2 = Math.multiplyExact(x, y);
System.out.println("wynik2 = " + wynik2);
} catch(ArithmeticException e) {
System.out.println(e);
}
}
}
package p03_zmienne_i_typy;
public class PrzeciazanieIntLong {
public static void main(String[] args) {
try {
System.out.println("oblicza w wersji int:");
System.out.println(Math.multiplyExact(5, 1000_000_000));
} catch(Exception e) {
System.out.println("wersja int: wyjątek " + e);
}
System.out.println();
try {
System.out.println("oblicza w wersji long:");
System.out.println(Math.multiplyExact(5L, 1000_000_000L));
} catch(Exception e) {
System.out.println("wersja long: wyjątek " + e);
}
}
}
package p03_zmienne_i_typy;
public class Rzutowania {
// "Hierarchia" typów prostych:
// byte < short < int < long < float < double
// char < int
public static void main(String[] args) {
int x = 107;
float f = 3.14f;
long l3 = 13;
// rzutowanie niejawne - na zmienną typu "szerszego" można zapisać wartość typu "węższego" (widening)
long l = x;
float f2 = l3;
//NK x = l;
//NK l = f;
f = l;
// rzutowanie jawne można stosować zawsze; czasem może wiązać się z "popsuciem" wartości liczbowej
x = (int)l;
System.out.println(x);
// można stosować jawne rzutowanie nawet gdy nie jest konieczne
l = x;
l = (long)x;
System.out.println(l);
l = 4_000_000_000L;
x = (int)l;
System.out.println(x); // zmieniona wartość, ostatnie 32 bity z zapisu tej liczby
f = 100.99F;
x = (int)f; // obcina do wartości całkowitej
System.out.println(x); // 100
f = 4e9f; // 4 * 10^9 czyli 4mld
x = (int)f; // po wyjściu poza zakres przyjmuje MAXINT / MININT
System.out.println(x);
// Na zmienne typu byte, short i char można wpisywać konkretne wartości całkowite, o ile kompilator widzi, że mieszczą się w zakresie
byte b1 = 100;
//NK byte b2 = 200;
x = 100;
//NK byte b3 = x;
final int fi = 10;
b1 = fi; // jeśli wartość jest "stałą" (jest final i jest znana w czasie kompilacji)
b1 = 50;
//NK b1 = x; // bo "nie każdy int mieści się w byte"
x = b1; // OK, bo byte mieści się w int
//NK int i3 = 3L;
float f3 = 3L;
byte b = 13;
b = 15;
//NK b = 130;
x = 15;
//NK b = x;
b = (byte)x;
//NK wezByte(88);
wezByte((byte)88);
wezByte(b);
System.out.println();
System.out.println(dajByte());
System.out.println(dajZnak());
System.out.println();
l = 5_000_000_000L;
x = (int)l;
System.out.println(x);
// rzutowanie liczb całkowitych - bierzemye ostatnie bity z zapisu liczby w pamięci
// zobaczę to samo, co w int overflow gdy mnożyłem 5 * 1000000000
System.out.println("5mld long rzut na int: " + x);
double d = 5_000_000_000.0;
x = (int)d;
System.out.println("5mld double rzut na int: " + x);
// rzutowanie float i double na liczbę całkowitą - bierzemy wartość, która jest najbliżej,
// w tym przypadku będzie to Integer.MAX_VALUE
byte b2 = 40, b3 = 50;
// Operacje arytmetyczne + - * / % - są zdefiniowane dla typu int, a nie dla byte i short
// dlatego ich ywniki trzeba zrzutowa, aby pisać na zmienne tych typów
//NK byte b4 = b2 + b3;
byte b4 = (byte)(b2 + b3);
// ale bez rzutowania działają ++ i +=
System.out.println(b2);
b2++;
System.out.println(b2);
b2 += 10;
System.out.println(b2);
}
static byte dajByte() {
return 65;
}
/* NK
static byte dajByteInaczej() {
int x = 65;
return x;
}
*/
static char dajZnak() {
return 65;
}
static void wezByte(byte bbb) {
System.out.println(bbb);
}
}
package p03_zmienne_i_typy;
public class WypiszZakresy {
public static void main(String[] args) {
System.out.println("byte " + Byte.BYTES + " bajtów, od " + Byte.MIN_VALUE + " do " + Byte.MAX_VALUE);
System.out.println("short " + Short.BYTES + " bajtów, od " + Short.MIN_VALUE + " do " + Short.MAX_VALUE);
System.out.println("int " + Integer.BYTES + " bajtów, od " + Integer.MIN_VALUE + " do " + Integer.MAX_VALUE);
System.out.println("long " + Long.BYTES + " bajtów, od " + Long.MIN_VALUE + " do " + Long.MAX_VALUE);
System.out.println("char " + Character.BYTES + " bajtów, od " + (int)Character.MIN_VALUE + " do "
+ (int)Character.MAX_VALUE);
System.out.println();
// bez ograniczen: klasy BigInteger (calkowite) i BigDecimal (z ulamkiem)
System.out.println("float " + Float.BYTES + " bajtów, od " + Float.MIN_VALUE + " do " + Float.MAX_VALUE);
System.out.println(" min normal : " + Float.MIN_NORMAL);
System.out.println("double " + Double.BYTES + " bajtów, od " + Double.MIN_VALUE + " do " + Double.MAX_VALUE);
System.out.println(" min normal : " + Double.MIN_NORMAL);
System.out.println();
System.out.println("boolean : false i true");
}
}
package p03_zmienne_i_typy;
public class Znaki {
public static void main(String[] args) {
System.out.println("A");
System.out.println("A" + 5);
System.out.println('A');
System.out.println('A' + 5);
System.out.println('A' + 'B');
System.out.println();
char c = 65; // można wpisywać konkretną wartość int, o ile mieści się w zakresie
//NK char d = -1;
int x = 65;
int y = 'A';
//NK c = x; // ale nie int-a ze zmiennej
c = (char)x;
System.out.println(c);
x = c;
System.out.println(x);
x = (int)c;
System.out.println((int)c);
System.out.println();
for(char znak = 'A'; znak <= 'Z'; znak++) {
System.out.print(znak + " ");
}
System.out.println();
int ącki = 'Ą';
System.out.println(ącki);
}
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment