Scrigroup - Documente si articole

     

HomeDocumenteUploadResurseAlte limbi doc
AccessAdobe photoshopAlgoritmiAutocadBaze de dateCC sharp
CalculatoareCorel drawDot netExcelFox proFrontpageHardware
HtmlInternetJavaLinuxMatlabMs dosPascal
PhpPower pointRetele calculatoareSqlTutorialsWebdesignWindows
WordXml


Utilizarea de clase si obiecte - Clase fara obiecte. Metode statice.

java



+ Font mai mare | - Font mai mic



Utilizarea de clase si obiecte

Clase fara obiecte. Metode statice.



Metodele Java sunt de doua categorii:

- Metode aplicabile obiectelor ("Object Methods")

- Metode statice, utilizabile independent de obiecte ("Class Methods")

O metoda statica Java corespunde unei functii din limbajul C, dar poate fi folosita numai precedata de numele clasei. In felul acesta putem avea functii cu acelasi nume in clase diferite si se reduce posibilitatea unui conflict de nume.

Cateva clase Java nu sunt altceva decat grupari de functii statice relativ independente. Aceste clase nu sunt instantiabile, deci nu pot genera obiecte. Metodele statice sunt in general si publice, pentru a putea fi apelate din orice alta clasa. Exemplu de utilizare a unor metode statice:

// afisare radical dintr-un numar primit in linia de comanda

class Sqrt

}

In Java se citesc din fisiere sau se preiau din linia de comanda siruri de caractere, iar analiza lor si conversia in format intern pentru numere se face explicit de catre programator. Din versiunea 1.5 au fost introduse in Java metode similare functiilor 'scanf' si 'printf' din C. Exemple:

System.out.printf ('%s %5dn', name, total); // afisare cu format

Scanner sc=Scanner.create(System.in); // citire cu format

String param= sc.next(); // metoda ptr citirea sirului urmator

int value=sc.nextInt(); // metoda ptr citirea urmatorului numar intreg

Pentru functiile matematice nu exista alta posibilitate de definire decat ca metode statice, deoarece ele primesc un parametru de un tip primitiv (double). Pentru metodele cu un operand de un tip clasa avem de ales intre o functie ne-statica si o functie statica. Metodele statice au un parametru in plus fata de metodele nestatice cu acelasi efect. Exemple:

// o metoda statica pentru conversie numar din Integer in int

public static int getInt (Integer a)

// exemplu de utilizare pentru conversie de la String la int

Integer a = new Integer (str);

int x = getint (a); // sau x = new Integer(str).intValue();

O metoda statica se poate referi numai la variabile statice din clase (variabile definite in afara functiilor si cu atributul static). Exemplu:

class A

}

Metoda "main" este statica si de aceea variabilele referite si metodele apelate direct trebuie sa fie statice (adica sa nu fie conditionate de existenta unor obiecte). In Java metodele statice sunt putine, iar variabile statice sunt in general constantele simbolice. In practica functia "main" creeaza unul sau cateva obiecte si apeleaza una sau cateva metode pentru obiectele create (de obicei "main" contine putine instructiuni). Exemplu de verificare a clasei "StrTok" definite anterior:

public static void main (String[] arg)

Metoda "main" de mai sus poate fi inclusa in clasa verificata StrTok sau poate fi in alta clasa.

Metode statice pot fi intalnite si in clase cu majoritatea metodelor nestatice, ca in exemplele urmatoare:

static Integer Integer.valueOf (String s); // conversie din String in Integer

static int Integer.parseInt (String s); // conversie din String in int

static String String.valueOf (int i); // conversie din int in String

static boolean Character.isDigit (char ch); // daca ch este cifra

static boolean Character.isLetter (char ch); // daca ch este litera

O metoda statica poate fi precedata de numele clasei sau de numele unei variabile de tipul clasei din care face parte (caz in care se apeleaza la fel ca o metoda nestatica). Exemple:

String s="-123"; Integer zero = new Integer(0);

int x = Integer.parseInt(s);

int y = zero.parseInt(s);

Multe functii recursive se scriu in Java ca metode statice, desi nu este imposibil sa avem si metode nestatice recursive. Pentru exemplificare vom defini o functie care sa afiseze fisierele dintr-un director dat si din subdirectoarele sale, care coboara recursiv in fiecare subdirector intalnit (metoda "listFiles" din clasa File nu furnizeaza decat fisierele si subdirectoarele de pe primul nivel):

static void printFiles (File d, String sp)

Clase instantiabile. Metode aplicabile obiectelor

Specific programarii orientate pe obiecte este utilizarea de clase care contin si date si care pot genera obiecte. O astfel de clasa poate fi privita ca un sablon pentru crearea de obiecte care au in comun aceleasi operatii (metode) dar contin date diferite. Un obiect este un caz particular concret al unei clase, deci o "instantiere" a unei clase. Intr-un program Java se creeaza obiecte si se apeleaza metode ale acestor obiecte. Toate obiectele sunt create dinamic, de obicei cu operatorul new.

Una din cele mai folosite clase in Java este clasa String, care poate genera obiecte ce contin fiecare un sir de caractere. Un obiect String poate fi creat pe baza unui vector intrinsec de caractere sau de octeti sau pe baza altui obiect String sau StringBuffer( StringBuilder). Clasa String contine metode pentru cautarea intr-un sir, pentru extragere de subsiruri, pentru comparatie de siruri si pentru anumite operatii de modificare a unui sir.

In Java obiectele sunt create dinamic, la executie, folosind direct operatorul new (sau apeland o metoda "fabrica" de obiecte). Adresa unui obiect se memoreaza intr-o variabila referinta de tipul clasei careia apartine obiectul. Exemple:

String fname = new String ("test.java "); // creare sir cu un nume de fisier

int p = fname.indexOf ('.'); // pozitia primului punct din nume

String fext = fname.substring (p+1); // creare sir cu extensia numelui

In exemplul de mai sus, metoda 'indexOf' se aplica obiectului cu adresa in variabila 'fname' si are ca rezultat un intreg, iar metoda 'substring', aplicata aceluiasi obiect are ca rezultat un alt obiect, memorat la adresa din variabila 'fext'.

Variabilele de un tip clasa reprezinta singura posibilitate de acces la obiectele Java si ele corespund variabilelor referinta din C++.

Pentru o scriere mai compacta se practica uneori inlantuirea de metode ("method chaining"), adica aplicarea unei metode asupra rezultatului unei alte metode, intr-o aceeasi expresie. Exemple:

String line = f.readLine().trim().toUpperCase(); // citeste linie, elimina spatii si trece in litere mari

if ( fname.substring(fname.indexOf('.')+1).toLowerCase().equals("java") )

Metoda "append" din clasele StringBuffer si StringBuilder au ca rezultat un obiect de acelasi tip cu obiectul pentru care se aplica metoda (este sirul rezultat prin adaugarea altor caractere sirului initial); de aceea este posibil sa inlantuim mai multe apeluri ale metodei "append" astfel:

StringBuilder sb = new StringBuilder();

sb.append ("x=").append(x).append (" y=").append(y);

System.out.println (sb);

Ordinea de evaluare pentru operatorul punct este de la stanga la dreapta (ca in C).

In Java gestiunea memoriei dinamice este automata iar programatorul nu trebuie sa aiba grija eliberarii memoriei alocate pentru obiecte. Teoretic, memoria ocupata de un obiect este eliberata atunci cand obiectul respectiv devine inaccesibil si inutilizabil, dar momentul exact al recuperarii memoriei nu poate fi precizat si depinde de modul de gestiune a memoriei dinamice.

Este posibila si apelarea directa a colectorului de resturi de memorie ("garbage collector"), dar nu se practica decat foarte rar.

Pentru utilizarea mai eficienta a memoriei si pentru reducerea timpului de executie se recomanda sa nu se creeze obiecte inutile, atunci cand exista alte posibilitati. De exemplu, o variabila de un tip clasa care va primi ulterior rezultatul unei functii nu va fi initializata la declarare cu altceva decat cu constanta null. Exemplu:

RandomAccessFile f = new RandomAccessFile ('date.txt','r');

String line=null; // nu: line = new String();

line = f.readLine(); // citeste o linie din fisierul f

O alta situatie este cea in care un vector de obiecte trebuie initializat cu un acelasi obiect (de fapt cu o referinta la un obiect unic):

Integer zero = new Integer (0); // un obiect de tip Integer

Integer count[ ]= new Integer [n]; // un vector cu elem. de tip Integer

for (int i=0; i<n;i++) count[i] = zero; // nu: count[i]= new Integer(0);

O a treia situatie frecventa este la construirea unui obiect pe baza altor obiecte; de obicei este suficienta retinerea adresei obiectului primit ca parametru de constructor si nu trebuie creat un nou obiect. Exemplu:

class Elev

. . . // metode ale clasei Elev

}

Variabile referinta la un tip clasa

Variabilele Java pot fi: variabile de un tip primitiv (char, int, float, boolean etc) sau variabile de un tip clasa (sau de un tip vector), care sunt variabile referinta. Nu se pot defini referinte la tipuri primitive sau parametri referinta de un tip primitiv.

Variabila care primeste rezultatul operatorului new nu contine chiar obiectul ci este o referinta la obiectul creat. O referinta la un tip T este de fapt un pointer la tipul T care se foloseste ca si cum ar fi o variabila de tipul T. Indirectarea prin variabila referinta este realizata automat de compilator, fara a se folosit un operator .


Simpla declarare a unei variabile de un tip clasa nu antreneaza automat crearea unui obiect. Compilatorul Java verifica si anunta utilizarea unei variabile care nu a fost initializata. Secventa urmatoare va provoca o eroare la compilare :

String nume;

System.out.println (nume); // utilizare variabila neinitializata

Variabilele declarate in functii nu sunt initializate de compilator, dar variabilele declarate in afara functiilor sunt initializate automat cu zero sau cu null. Exemplu de eroare care nu este semnalata la compilare si produce o exceptie la executie:

class Eroare

}

Pentru elementele unui vector intrinsec compilatorul nu poate stabili daca au fost sau nu initializate si se produce exceptie la executie. Exemplu:

String tab[ ] = new String[10]; // tab[i]=null in mod implicit

int n=tab[0].length(); // NullPointerException

Utilizarea operatorului de comparatie la egalitate '==' intre doua variabile referinta are ca efect compararea adreselor continute in cele doua variabile si nu compararea datelor adresate de aceste variabile. Exemplu de eroare:

String linie=f.readLine(); // citeste o linie din fisierul f

if (linie == ".") break; // incorect, se compara adrese !

Comparatia la egalitate intre obiecte Java se face prin metoda 'equals' (de tip boolean).Exemplu :

if (linie.equals (".")) break; // "linie" de tip String

Metoda "equals" exista in orice clasa Java iar metoda "compareTo" (cu rezultat "int") exista numai in clasele cu obiecte "comparabile", cum sunt clasele String, Integer, Float, Date etc.

Operatorul de atribuire se poate folosi numai intre variabile referinta de acelasi tip sau pentru atribuirea constantei null la orice variabila referinta. Efectul atribuirii intre doua variabile referinta este copierea unei adrese si nu copierea unui obiect. Atribuirea intre variabile referinta duce la multiplicarea referintelor catre un acelasi obiect. Exemplu:

StringBuffer s2, s1=new StringBuffer ("unu");

s2=s1; // adresa sirului "unu"

s2.append ("doi");

System.out.println (s1); // scrie: unudoi


Copierea datelor dintr-un obiect intr-un alt obiect de acelasi tip se poate face:

a) Prin construirea unui nou obiect pe baza unui obiect existent (daca exista constructor):

String s1 = "unu"; String s2 = new String (s1);

b)      Prin construirea unui nou obiect care preia datele din vechiul obiect (daca exista metode de extragere a datelor dintr-un obiect). Exemplu:

Integer m1 = new Integer(1);

Integer m2 = new Integer ( m1.intValue());

c) Folosind metoda generala "clone" (mostenita de la clasa Object), dar numai pentru obiecte din clase care implementeaza interfata Clonable. Exemplu:

Vector a, b; // referinte la doi vectori

b= (Vector) a.clone(); // creare b si copiere date din a in b

In metoda "clone" se aloca memorie pentru un nou obiect si se copiaza datele din obiectul vechi in noul obiect ( rezultat al metodei "clone"). Copierea este superficiala in sensul ca se copiaza variabile referinta (pointeri) si nu datele la care se refera acele variabile. Un rezultat nedorit este aparitia unor obiecte cu date comune.

Clasele JDK care contin variabile de un tip referinta au metoda "clone" redefinita pentru a face o copiere "profunda" a datelor din obiectul clonat in obiectul clona.

Incercarea a utiliza o variabila referinta cu valoarea null pentru apelarea unei metode cauzeaza exceptia NullPointerException. Exemplu:

String s=null; int len = s.length(); // exceptie !

Elementele unui vector de obiecte sunt initializate automat cu null la alocarea de memorie, iar prelucrarea unui vector completat partial poate produce exceptia de utilizare a unui pointer (referinta) cu valoarea null. Exemplu:

Object a[] = new Object [10] ; // 10 valori null

a[0]='unu'; a[1]='doi'; a[2]='trei';

Arrays.sort(a); // exceptie aruncata de functia "sort"

Metoda "clone" de copiere a unui vector intrinsec nu copiaza si valorile null, retinand in vectorul clona numai elementele nenule. Exemplu:

Object [ ] b = new Object[10];

b = (Object[]) a.clone();

Arrays.sort (b); // nu produce exceptie

Clonarea de obiecte este o operatie folosita destul de rar in practica programarii. O situatie in care pare necesara clonarea este la transmiterea de obiecte pentru construirea altor obiecte, cum ar fi transmiterea unui sir la construirea unui obiect de tip StrTok (sau StringTokenizer). Constructorul StrTok retine o referinta catre sirul de analizat si nu face o copie a acestui sir, pentru ca nu modifica sirul primit.

Intr-un vector sau intr-o alta colectie se memoreaza referinte catre obiecte si nu catre clone ale obiectelor, pentru a permite modificarea obiectelor din colectie. Un exemplu este un vector de vectori, care sa permita modificarea oricarui vector, ca si a obiectelor memorate in acesti vectori. Situatia este similara unui vector de pointeri din limbajul C (catre siruri sau catre diferite structuri alocate dinamic): nu se cloneaza structurile sau sirurile, iar adresele lor sunt memorate in vector).

Argumente de functii de tip referinta

In Java, ca si in C, transmiterea unui parametru efectiv la apelarea unei functii se face prin valoare, adica se copiaza valoarea parametrului efectiv in parametrul formal corespunzator, inainte de executia instructiunilor din functie. Argumentele de un tip primitiv nu pot fi modificate de o metoda Java, deci o metoda nu poate transmite mai multe rezultate de un tip primitiv, dar acest lucru nici nu este necesar. Argumentele unei metode sunt de obicei date initiale, iar efectul metodei este modificarea variabilelor clasei si nu modificarea argumentelor.

In cazul parametrilor de un tip clasa (parametri referinta) se copiaza adresa obiectului din functia apelanta in parametrul formal si nu se copiaza efectiv obiectul.

Prin copierea adresei unui obiect in parametrul formal corespunzator apar referinte multiple la un acelasi obiect (multiplicarea referintelor). O functie nu poate trasmite in afara adresa unui obiect creat in functie printr-un parametru referinta. Exemplu de functie fara efect in afara ei:

// metoda statica pentru trecere sir in litere mari - gresit !!!

static void toUpper (String t)

Aici se creeaza un obiect String prin metoda "toUpperCase", iar adresa sa este memorata in variabila locala "t" (care continea initial adresa sirului dat). Un obiect creat intr-o functie trebuie transmis ca rezultat al functiei. Exemplu:

static String toUpper (String s)

O functie poate modifica un obiect a carui adresa o primeste ca argument numai daca in clasa respectiva exista metode pentru modificarea obiectelor.

Avantajele si riscurile obiectelor modificabile trasmise ca argumente pot fi ilustrate prin clasa BitSet, pentru multimi de intregi realizate ca vectori de biti. Diferenta a doua multimi A-B poate fi realizata prin functia urmatoare:

public static void minus (BitSet a, BitSet b)

Daca vrem sa pastram multimea "a" atunci vom transmite o copie a ei

BitSet aux= (BitSet) a.clone(); // copiaza pe a in aux

minus (aux,b); // aux = aux-b

In exemplul urmator diferenta A-B se obtine pe baza unor operatii existente: A-B = A / (A*B) unde A/B este diferenta simetrica a multimilor A si B. Functia modifica in mod nedorit multimile primite ca argumente din cauza multiplicarii referintelor.

public static BitSet minus (BitSet a, BitSet b)

Urmeaza o varianta corecta pentru calculul diferentei a doua multimi de tip BitSet:

public static BitSet minus (BitSet a, BitSet b)

Clase cu obiecte nemodificabile

Clasele String, Integer, Float s.a. nu contin metode pentru modificarea datelor din aceste clase, deci o functie care primeste o referinta la un astfel de obiect nu poate modifica acel obiect. In acest fel se protejeaza obiectul transmis ca argument fata de modificarea sa nedorita de catre functia care il foloseste. Obiectele din clase fara metode de modificare a datelor (clase "read-only") se numesc obiecte nemodificabile ("immutable objects"). Clasa String este o clasa read-only si finala, deci nu se poate extinde cu metode de modificare a vectorului de caractere continut in fiecare obiect.

Exemplu de utilizare gresita a metodei "replaceAll" din clasa String pentru inlocuirea unui subsir s1 cu un alt subsir s2 in sirul s:

s.replaceAll (s1,s2);

Metodele "replaceAll" si "replace" au ca rezultat un nou sir obtinut dupa substituire si nu modifica obiectul pentru care se apeleaza; de aceea utilizarea corecta este urmatoarea:

s = s.replaceAll (s1,s2);

Clasele StringBuffer si StringBuilder (din 1.5) sunt variante ale clasei String care contin in plus si metode pentru modificarea obiectului (sirului). Exemple de metode care modifica sirul continut intr-un obiect de tip StringBuffer: append, insert, delete, setCharAt, setLength. Un obiect de tipul StringBuffer transmis unei functii ca argument poate fi modificat de catre functie. Varianta pentru functia "toUpper":

static void toUpper (StringBuffer s)

Clasa StringBuilder este mai performanta decat StringBuffer pentru programele fara fire de executie multiple, dar exista numai din versiunea 1.5.

Concatenarea de siruri este o operatie frecventa in Java. Metoda "println" folosita pentru afisarea pe ecran poate avea un singur argument de tip String. Pentru a scrie mai multe siruri acestea se concateneaza intr-un singur sir cu operatorul '+'.Exemplu:

System.out.println ( "x= " + x); // x de orice tip

Intr-o expresie cu operatorul binar '+', daca unul din operanzi este de tip String, atunci compilatorul Java face automat conversia celuilalt operand la tipul String (pentru orice tip primitiv si pentru orice tip clasa care redefineste metoda "toString").

Aceasta observatie poate fi folosita si pentru conversia unui numar in sir de caractere, ca alternativa a utilizarii metodei "valueOf" din clasa String. Exemplu:

float x = (float) Math.sqrt(2);

String str = ""+x; // sau str = String.valueOf(x);

O instructiune de forma a=a+b; cu "a" si "b" de tip String este tratata de compilator astfel: se transforma obiectele a si b in obiecte de tip StringBufer, se apeleaza metoda "append" si apoi creeaza un obiect String din obiectul StringBuffer rezultat din concatenare:

// secventa echivalenta cu a=a+b;

String a="unu", b="doi";

StringBuffer am= new StringBuffer (a), am.append(bm);

a= new String (am);

Daca trebuie sa facem multe concatenari de siruri este preferabil ca timp sa se foloseasca direct metoda "append" din clasa StringBuilder (StringBuffer). Exemplu:

public static String arrayToString ( int a[ ])

De observat ca, mai nou, exista in clasa Arrays metoda statica "toString" cu argument vector.

Eliminarea unui subsir dintr-un sir se poate face folosind metoda "delete" din clasa StringBuffer sau cu metode ale clasei String. Exemplu:

// sterge caractere dintre pozitiile "from" si "to" din sirul s

static String delete1 (String s, int from, int to )

// varianta cu StringBuffer

static String delete2 (String s, int from, int to )

De observat ca trecerea de la tipul String la tipul StringBuffer se poate face numai printr-un constructor, dar trecerea inversa se poate face prin metoda "toString", iar aceste transformari pot fi necesare pentru ca in clasa StringBuffer nu se regasesc toate metodele din clasa String.

Metoda "toString" exista in toate clasele ce contin date si produce un sir cu datele din obiectul pentru care se apeleaza (face conversia de la tipul datelor din obiect la tipul String).

Metode statice si metode ale obiectelor

Utilizarea abuziva de metode statice este o prelungire a programarii procedurale in limbajele orientate obiect. Utilizarea de metode obiect (nestatice) permite utilizarea unor tehnici specifice programarii cu obiecte: derivare, mostenire, polimorfism, programare cu interfete, s.a. Avantajele metodelor obiect sunt mai evidente in cazul unor familii de clase deschise pentru extindere si atunci cand se urmareste reutilizarea metodelor unor clase in alte clase.

Pentru a arata diferentele sintactice dintre definirea si utilizarea celor doua tipuri de metode vom folosi exemplul unei clase cu rolul clasei StringTokenizer, dar fara posibilitatea de a specifica lista de caractere separator intre atomi; atomii sunt separati numai prin spatii albe.

class StrTok

// extrage urmatorul atom lexical dintr-un sir

public static int nextToken (String str, int pos, String tok[])

}

// utilizare clasa StrTok

class UseStrTok

}

}

Am folosit un vector cu un singur element ca artificiu pentru a permite functiei "nextToken" sa transmita unul din rezultate (urmatorul atom extras) printr-un argument, lucru imposibil printr-un argument de tip String. Functia are doua rezultate: atomul extras si pozitia din sir de dupa acest atom.

Urmeaza varianta cu metode ale obiectelor:

class StrTok

// daca mai sunt atomi in sirul analizat

public boolean hasMoreTokens ()

// extrage urmatorul atom lexical dintr-un sir

public String nextToken ()

}

// utilizare

class UseStrTok

}

}

Utilizarea unor clase de citire-scriere

Exista un numar relativ mare de clase Java pentru operatii de intrare-iesire cu fisiere dar aici vom da cateva "retete" simple pentru realizarea de aplicatii Java de tip "Desktop" (de tip consola) cu clase din pachetul java.io.

Afisarea pe ecran si scrierea in fisiere text a oricarui tip de date se face simplu folosind metodele "print" si "println" din clasele PrintStream sau PrintWriter. Aceste metode pot primi un singur argument de orice tip primitiv sau de tipul generic Object si realizeaza automat conversia numerelor din format intern in format extern (sir de caractere).

Toate clasele de I/E pentru operatii cu fisiere disc au constructori cu argument String si respectiv File pentru a primi numele fisierului disc cu care lucreaza. Toate clasele au metode de citire a unui caracter (sau octet) si de scriere a unui caracter sau octet. Constructorii si metodele acestor clase pot genera exceptii IOException, care trebuie aruncate sau tratate (prin try. catch).

Pentru a scrie intr-un fisier disc se creeaza mai intai un obiect FileInputStream sau FileWriter si apoi se creeaza obiectul PrintStream sau PrintWriter. Exemple:

try catch (IOException e)

Pentru scrierea de siruri in fisiere text se poate utiliza direct metoda "write (String)" din clasa FileWriter, dar pentru a scrie linii de text trebuie adaugat explicit caracterul 'n'. Exemplu:

try catch (IOException e)

Nu exista o clasa de citire date corespondenta cu PrintStream sau PrintWriter, care sa faca conversie automata de numere la citire (din sir de caractere zecimale in format intern binar), dar din versiunea 1.5 s-a introdus clasa Scanner in pachetul java.util pentru astfel de operatii.

Citirea de siruri de la tastatura sau dintr-un fisier text se poate face in doua moduri:

- Folosind metoda "read" din clasa FileReader pentru citire intr-un vector de octeti urmata de conversie la tipul String;

- Folosind metoda "readLine" din clasa BufferedReader sau BufferedInputStream pentru citire din fisiere text formate din linii (linii terminate prin caracterul 'n').

Exemple de citire integrala in memorie a unui fisier text:

try catch (IOException e)

Semnificatia si ordinea argumentelor metodei "read" sunt aceleasi ca intr-un constructor al clasei String, astfel ca se poate trece simplu de la un vector de caractere de lungime cunoscuta la un String.

Exemplu de citire linii de text:

String line; // aici se citeste o linie de text

try catch (Exception e)

Variabila publica System.out este de tip PrintStream dar variabila System.in este de tip InputStream, pentru care se poate folosi metoda "read" de citire a unui octet sau a unui vector de octeti de lungime specificata. Pentru a citi linii de text de la consola vom folosi o clasa care contine o metoda "readLine": BufferedReader sau DataInputStream.

String line;

try catch( IOException e)

Pentru citirea de numere de la consola sau din fisiere text trebuie folosita o metoda de conversie cu argument String, cum sunt Integer.parseInt, Float.parseFloat, Double.parseDouble.

Clasa RandomAccessFile are o serie de avantaje fata de alte clase de I/E:

- permite atat operatii de scriere cat si operatii de citire;

- permite crearea si citirea de fisiere binare, cu numere in format intern (readInt, writeInt, etc.);

- permite citirea de linii de text (readLine);

- permite accesul direct la date din fisier pe baza adresei de octet in fisier (seek), aflarea adresei curente in fisier (getFilePointer) si aflarea lungimii unui fisier (length).

- permite citirea unui intreg fisier in memorie (readFully).

Exemplu de citire si scriere linii de text folosind obiecte de tip RandomAccessFile:

public static void main (String[] arg) throws IOException

In general, metodele de citire din clasele Java raporteaza prin rezultatul lor cand se ajunge la sfarsitul fisierului si nu exista metode care sa testeze sfarsitul de fisier. Aceasta regula nu se aplica si metodelor care citesc numere din fisiere binare deoarece rezultatul (valoarea citita) poate fi orice configuratie binara; solutia este sa se compare pozitia curenta in fisier cu lungimea fisierului:

while (f1.getFilePointer() < f1.length() )

Deoarece clasa RandomAccessFile este definita in afara familiilor de clase de I/E, acest tip nu apare ca posibil argument in constructorii altor clase care folosesc fisiere disc: clase pentru compresie si arhivare de fisiere, clase parser de fisiere text sau de fisiere XML, s.a. Acesti constructori au fie un argument File, fie un argument clasa abstracta Reader (InputStream) sau Writer (OutputStream).

Clasa Scanner are metode ca nextInt, nextFloat, nextDouble, s.a care se folosesc oarecum similar functiei "scanf" din limbajul C, deci programatorul trebuie sa stie ce tip de date urmeaza sa citeasca:

Scanner sc = new Scanner (new FileReader (arg[0]));

int x, sum=0;

while ( sc.hasNext( ))

Exista si un corespondent al functiei "printf" sub forma metodei "format" din clasele String si java.util.Formatter, dar ca si in cazul functiei "printf" exista multe detalii legate de precizarea formatului dorit.



Politica de confidentialitate | Termeni si conditii de utilizare



DISTRIBUIE DOCUMENTUL

Comentarii


Vizualizari: 1424
Importanta: rank

Comenteaza documentul:

Te rugam sa te autentifici sau sa iti faci cont pentru a putea comenta

Creaza cont nou

Termeni si conditii de utilizare | Contact
© SCRIGROUP 2024 . All rights reserved