Java:Muutujad

Allikas: Kursused
Mine navigeerimisribale Mine otsikasti

Muutuja (ingl variable) on nimeline viide mingile väärtusele, mis paikneb kuskil mälus. Näiteks võib muutuja nimi olla x ja see viitab väärtusele 5. Pseudokoodina võib kirjutada, et x = 5 (tegelikult samamoodi saab matemaatikas muutuja väärtust määrata). Kui edaspidi kuskil kasutatakse x'i, siis on selle väärtus 5. Näiteks x + 3 on väärtuse poolest sama mis 5 + 3. Analoogselt võib mõelda näiteks Exceli lahtritele. Kui te seal kirjutate mingeid valemeid, siis teete seda selliselt: =A1 + B2. A1 ja B2 oleksid nagu muutujad, mille väärtus on vastavates lahtrites.

Javas on igal muutujal lisaks nimele ka andmetüüp. Kui näiteks Pythonis võib kirjutada x = 'tere' ja seejärel kohe x = 3, siis Javas tuleb kõigepealt muutuja tüüp määrata. Edaspidi tohib see muutuja ainult seda tüüpi andmeid hoida. Näiteks täisarvuline andmetüüp on int: int x = 3;. Edaspidi koodis, kui ma olen juba x-ile andmetüübi määranud, saan ma kasutada lihtsalt muutujat (ilma andmetüübita): x = 4;. Viimane näide oli selline, kus deklareeriti muutuja x ning sellele anti kohe väärtuseks 3. Seejärel muudeti x'i väärtus 4-ks.

Sama nimega muutujaid tohib olla vaid üks. Kui koodis on deklareeritud muutuja x, siis rohkem selles koodiosas ei tohis x-nimelist muutujat olla.

Andmetüübid

Andmetüübid Javas jagunevad kahte suuremasse klassi: primitiivsed andmetüübid ja objektid. Esialgu vaatleme primitiivseid andmetüüpe. Primitiivsete andmetüüpide korral kehtib reegel, et muutujal on konkreetne väärtus. Hiljem objektide puhul näeme, mismoodi see on erinev.

All tabelis on välja toodud erinevad primitiivsed andmetüübid Javas:

ITI0011-prax-02-datatypes.png

Tüübi nimi Suurus Väärtused Näide
byte 1 bait (8 bitti) -128..127 byte b = 42;
short 2 baiti (16 bitti) -32768..32767 short s = -12345;
int 4 baiti (32 bitti) -2 147 483 648 (-2^31).. 2 147 483 647 (2^31 - 1) int i = 10;
long 8 baiti (64 bitti) -2^63 .. (2^63 - 1) long l = -100;
float 32-big floating point * float f = 3.14f;
double 64-bit floating point * double d = 1.2345;
boolean 1 bitt true, false boolean b = true;
char 16-bit character 'a', 'b', ... char c = 'a';

Muutuja deklareerimine, väärtustamine

Muutuja deklareerimine ehk muutuja tutvustamine programmile käib selliselt:

[andmetüüp] [muutujanimi];

või


[andmetüüp] [muutujanimi] = [algväärtus];

Näiteks:

int y; int x = 10;

Edaspidi igal ajal koodis võib muutuja väärtust muuta:

y = 1; x = 3;

Muutujate nimetamine

Java keeles lubatud muutuja nimed: N, n, x15, a_long_name, time_is_$, HelloWorld. Muutuja nimi on tõstutundlik, ehk siis kõik järgmised on erinevad muutujad: HelloWorld, helloWorld, helloworld, HELLOWORLD, HeLLoWoRLd. Keelekonstruktsioonide nimetused on reserveeritud, seetõttu nimed nagu class, public, static, if, else jne ei ole lubatud.

Kuigi Javas on lubatud väga erinevad nimekujud, on soovitatav järgida neid reegleid:

  • muutuja nimi peaks olema mõistlik (temperature, speed mitte a, b)
  • nimi peaks algama väikese tähega
  • kasutada tuleks täisnimetusi (temperature, mitte temp)
  • kui nimi koosneb ühest sõnast, siis kasutada läbivat väiketähte: weight, speed.
  • kui nimi koosneb kahest või rohkemast sõnast, siis kirjutatakse sõnad kokku ning alates teisest sõnast iga sõna esimene täht peaks olema suur: playAgain, currentSpeed.

Kuna keelekonstruktsioonid on kõik inglisekeelsed (if, while, class jne), siis on soovitatav kasutada inglisekeelseid muutujanimesid (speed, mitte kiirus). Igal juhul võiks loogika olla läbi koodi sama: kui alustasite eestikeelsete muutujanimedega, siis peaks sama loogika kehtima lõpuni. See, kus mõned muutujad on eestikeelsed ja mõned inglisekeelsed, on väga halb komme.

Konstandid

Konstandid on erilisttüüpi muutujad. Nad on samamoodi andmetüübiga ja nimega viited mingile väärtusele. Erinevus tavalisest muutujast on see, et konstandi väärtust ei saa hiljem enam muuta. Konstandi nimetamise reeglid on mõnevõrra erinevad tavamuutujast:

  • kõik tähed nimes on suurtähed: PI, SPEED.
  • sõnad on eristatud alakriipsuga (_): SPEED_OF_LIGHT, NUMBER_OF_GEARS.

Konstandi saab luua klassi päises (enne meetodeid/funktsioone): public static final double PI = 3.14;

Konstanti kasutatakse koodis mingi konkreetse väärtuse asendamiseks. Võrrelge kahte järgmist koodi:

Ilma konstantideta: <source lang="java"> public class KonstantPuudu {

public static void main(String[] args) { int x = readInput(); if (x == 5) { makeMove(2, 4); }

} } </source>

Konstantidega: <source lang="java"> public class Konstant { private static final int ACTION_MOVE = 5; private static final int PLAYER_O = 1; private static final int PLAYER_X = 2; private static final int MOVE_LEFT = 4; private static final int MOVE_RIGHT = 6;

public static void main(String[] args) { int x = readInput(); if (x == ACTION_MOVE) { makeMove(PLAYER_X, MOVE_LEFT); }

} }

</source>

Viimane kood on selgemini loetav. Esimese näite puhul ei saanud aru, mida need 2 ja 4 jm numbrid tähendavad. Nüüd on aru saada, millega umbes on tegemist.

Kui koodis on mõnda väärtust mitu korda kasutatud (näiteks pi väärtus) numbrina, on selle hilisem muutmine täpsemaks palju keerulisem (tuleb kõik esinemised ära muuta). Kui kasutate konstanti oma koodis, piisab vaid konstandi muutmisest ja kõikides kohtades, kus konstant on kasutusel, muutub vastav väärtus.

Magic number

Checkstyle lisa Eclipse'ile annab aeg-ajalt teate "Magic number" kohta. See teade tähendab seda, et checkstyle ei soosi numbrite kasutamist koodis. Iga number peaks olema asendatud konstandiga. Üldiselt igal numbril on mingi tähendus, see tulekski konstandi nimeks panna ja asendada number vastava konstandiga. Vt #Konstandid

Operatsioonid, tehted

ITI0011-prax-02-operators.png

Muutuja suurendamine/vähendamine ühe võrra:

  • y = x++ (x suurendatakse peale omistamist)
    • y = x
    • x = x + 1
  • y = ++x (x suurendatakse enne omistamist)
    • x = x + 1
    • y = x
  • x += y
    • x = x + y

Tehete järjekord (mis vastus on?):

  • x = 2 + 3 * 6;
  • x = (2 + 3) * 6;

Jagamine, jääk

Kui argumendid on täisarvud, on ka tulemus täisarv (võetakse täisosa, mitte ei ümardata):

  • 6 / 5 = 1
  • 3 / 5 = 0
  • 10 / 5 = 2

Kui vähemalt üks argumentidest on komaga arv, on tulemus ka komaga arv:

  • 6.0 / 5 = 1.2
  • 3 / 5.0 = 0.6
  • 10.0 / 5.0 = 2.0

Jääk jagamisel (%):

  • 22 % 5 = 2 (22 / 5 on 4, jääk on 2)
  • 5 % 5 = 0
  • 3 % 5 = 3

Jäägist võib mõelda nii, et kui meil on 22 õuna ja peame need 5 inimese vahel jagama (õunu katki ei tohi teha), siis mitu õuna jääb üle. Või kui meil on 3 õuna, siis 5-le inimesele jagatuna saab igaüks 0, 3 jääb üle.

Cast'imine

Kui muutujat on vaja kasutada teise andmetüübina, võib kasutada cast'imist. Näiteks täisarvude puhul saab kasutada, et saada "normaalne" tulemus.

  • x = 8; y = 5; x / y = 1 (aga tahaksime saada 1.6)

Cast'imine ei muuda muutuja väärtust.

Cast'imise süntaks:

([uus-tüüp])[muutuja-nimi-või-väärtus];

Näide: <source lang="java"> (double)8/5; // => 1.6 x = 5; y = 2; x / y; // => 5 / 2 = 2 (double)x / y // => 5.0 / 2 = 2.5 x / y; // => 5 / 2 = 2 (int)5.5 / 3 // => 5 / 3 = 1 </source>

Muutuja skoop

Javas hakkab üldiselt muutuja kehtima sellest hetkest (reast), kui muutuja deklareeritakse. Enne deklareerimise rida muutujat kasutada ei saa:

<source lang="java">

// .. // System.out.println(x); <- annaks vea, kuna muutujat x pole deklareeritud int x = 10; System.out.println(x); // prindib 10, muutuja x on ilusti olemas // .. </source>

Muutuja kehtib alates deklareerimisest kuni selle ploki, mille sees see deklareeriti, lõpuni. Näiteks <source lang="java" line> public static void main(String[] args) { int a = 10; if (a > 5) { int uus = 11; System.out.println(uus); } else { // System.out.println(uus) annab vea } // System.out.println(uus) annab vea } </source>

a deklareeritakse 2. real ja ta kehtib main meetodi lõpuni (koodinäite lõpuni). Muutuja uus deklareeritakse if-lause sees (4. rida) ning ta lõppeb ära 6. real (if osa lõpus). Kui proovime muutujat uus kutsuda välja kas else osas või üldse peale if lause plokki, saaksime vea, kuna muutuja seal enam ei kehti.

Seega, kõik muutujad, mis te funktsiooni/meetodi sees deklareerite, kehtivad maksimaalselt selle funktsiooni/meetodi lõpuni. Kui teil on vaja kasutada muutujat, mis oleks kättesaadav ka teistele funktsioonidele, kasutage klassimuutujat.

Klassimuutujad

Kui te deklareerite funktsiooni/meetodi sees muutuja, on see n-ö lokaalne muutuja - see kehtib vaid selle funktsiooni sees. Kui deklareerite muutuja väljaspool funktsiooni/meetodit (aga klassi-ploki sees), nimetatakse seda klassimuutujaks (hiljem räägime eraldi objekti muutujatest). Klassimuutuja kirjeldatakse ära näiteks selliselt:

<source lang="java"> public class Muutujad {

public static int x = 10;

public static void main(String[] args) { // ... } </source>

Nagu näha, siis muutuja deklaratsiooni rida näeb mõnevõrra pikem välja. Lisaks tavapärasele andmetüübile ja muutuja nimetusele int x, sisaldab klassimuutuja deklaratsioon veel kahte märksõna: public static. Kui public pole otseselt vajalik, siis static praegusel juhul on.

Kui mõelda muutuja skoobi peale, siis võiks klassimuutuja hakata kehtima sellest reast, kus ta deklareeritakse, ning kehtida kuni ploki lõpuni. Plokk, milles klassimuutuja deklareeritakse, ongi klass ise. Seega muutuja kehtib kuni faili (klassi) lõpuni. Klassimuutuja hakkab kehtima juba klassi algusest (sõltumata sellest, mitmendal real ta klassi sees deklareeritakse). Klassimuutuja deklaratsioon võib olla ka viimane rida klassi kirjelduses, ikka hakkab ta kehtima esimesest klassi reast.

Näide: <source lang="java"> public class Muutujad {

public static int x = 10;

public static int f() { System.out.println(x); // 10 return 0; }

public static int g() { System.out.println(x); // 10 int x = 5; System.out.println(x); // 5 return 0; }

public static int h(int x) { System.out.println(x); // argumendi x väärtus. ehk kui kutsutakse välja h(6), siis prindib 6. return 0; }

} </source>