CodeGym /Kurslar /JAVA 25 SELF /Fayllarla iş rejimləri: oxuma, yazma, əlavə yazma

Fayllarla iş rejimləri: oxuma, yazma, əlavə yazma

JAVA 25 SELF
Səviyyə , Dərs
Mövcuddur

1. Üzərinə yazma

Fayllarla işləyərkən başa düşmək vacibdir ki, «fayla yazmaq» — həmişə eyni şey deyil. Bəzən faylı tam yenidən yazmaq lazımdır (məsələn, yeni hesabatı saxlayanda), bəzən isə mövcud faylın sonuna yeni məlumatı əlavə etmək gərəkir (məsələn, tətbiqin hadisə jurnalını aparmaq). Bəzi hallarda isə faylın məzmununu sadəcə oxumaq kifayətdir, onu dəyişmədən.

Java-da (xüsusilə müasir java.nio.file paketində) faylla iş rejimi yazma metodlarına verdiyiniz xüsusi seçimlər toplusu ilə təyin olunur, məsələn, Files.write() metodunda. Bu seçimlər faylı yenidən yazmaq istədiyinizi, yoxsa sonuna nəsə əlavə etmək istədiyinizi açıq şəkildə göstərməyə imkan verir.

Bu necə işləyir

Files.write(path, data) çağırdıqda, Java, susmaya görə, yeni fayl yaradır və ya mövcud faylı yenidən yazır. Faylın bütün köhnə məzmunu silinir və yerinə yalnız yeni məlumat yazılır.

Bu, susmaya görə davranışdır — fayl üçün bir növ «sərt sıfırlama» kimidir. Əgər faylda əvvəllər 1000 sətir var idisə, siz isə bir sətir yazdınızsa — əvvəlki hər şey izsiz yox olacaq.

Nümunə: sətiri fayla yazmaq

import java.nio.file.*;
import java.io.IOException;
import java.util.List;

public class OverwriteFileExample {
    public static void main(String[] args) throws IOException {
        Path path = Paths.get("myfile.txt");
        List<String> lines = List.of("Salam, dünya!", "Bu faylda yeni yazıdır.");

        // Sətirləri fayla yazırıq (köhnə məzmun silinəcək)
        Files.write(path, lines);

        System.out.println("Fayl uğurla yenidən yazıldı!");
    }
}

Bu kodu işə saldıqdan sonra myfile.txt faylında yalnız lines siyahısındakı iki sətir qalacaq. Əvvəllər olan hər şey yox olacaq (Java tərəfindən heç bir «heyfslənmə» yoxdur).

2. Əlavə yazma (append): məlumatı faylın sonuna əlavə etmək

Bəzi tapşırıqlarda (məsələn, hadisə jurnalının aparılması, loglama, verilənlərin toplanması) faylın köhnə məzmununu silmək yox, yeni sətirləri sona əlavə etmək lazımdır. Köhnə API-də bunun üçün tez-tez FileWriter append = true flaqı ilə istifadə olunurdu. Müasir API-də isə hər şey daha sadə və aydındır.

Bu necə edilir

Sadəcə StandardOpenOption.APPEND seçimini Files.write() metoduna verin:

import java.nio.file.*;
import java.io.IOException;
import java.util.List;

public class AppendFileExample {
    public static void main(String[] args) throws IOException {
        Path path = Paths.get("myfile.txt");
        List<String> moreLines = List.of("Daha bir sətir əlavə etdik.", "Və birini də!");

        // Sətirləri faylın sonuna əlavə edirik (köhnə məzmun qalır)
        Files.write(path, moreLines, StandardOpenOption.APPEND);

        System.out.println("Sətirlər faylın sonuna əlavə olundu!");
    }
}

Vacib məqam: əgər fayl mövcud deyilsə, əlavə yazmağa cəhd edərkən xəta baş verəcək — Java APPEND rejimində faylı avtomatik yaratmayacaq. Faylı yoxdursa yaratmaq üçün iki seçimi birlikdə istifadə edin:

Files.write(path, moreLines, StandardOpenOption.APPEND, StandardOpenOption.CREATE);

Bu praktikada necə görünür

  • Proqramı yazma (üzərinə yazma) rejimində işə salırsınız — faylda iki sətir olur.
  • Proqramı əlavə yazma ilə işə salırsınız — həmin sətirlərə yeniləri artırılır, köhnələr yerində qalır.

3. Seçimlərin kombinasiyası: CREATE, APPEND, TRUNCATE_EXISTING

Java-da faylı açma rejimlərini daha çevik idarə etmək üçün bir neçə seçimi kombinə etmək mümkündür:

  • StandardOpenOption.CREATE — fayl yoxdursa, yarat.
  • StandardOpenOption.APPEND — məlumatı sona əlavə et.
  • StandardOpenOption.TRUNCATE_EXISTING — fayl mövcuddursa, onu sıfır bayta qədər kəs (təmizlə).
  • StandardOpenOption.CREATE_NEW — yeni fayl yarat; artıq mövcuddursa — xəta.

Nümunə: fayl yoxdursa yarat və məlumatı sonuna əlavə et

Files.write(path, moreLines, StandardOpenOption.CREATE, StandardOpenOption.APPEND);

Nümunə: faylı yarat və ya tam təmizlə, sonra yeni məlumat yaz

Files.write(path, lines, StandardOpenOption.CREATE, StandardOpenOption.TRUNCATE_EXISTING);

Cədvəl: əsas yazma rejimləri

Seçim(lər) Davranış
(susmaya görə) Fayl yaratmaq və ya mövcud olanın üzərinə yazmaq
APPEND
Sona əlavə et, fayl yoxdursa — xəta
APPEND + CREATE
Sona əlavə et, fayl yoxdursa yarat
TRUNCATE_EXISTING
Faylı sıfıra qədər kəs və yeni məlumatları yaz
CREATE_NEW
Yeni fayl yarat, fayl artıq mövcuddursa — xəta

4. Binar faylların oxunması və yazılması

İndiyədək sətirlərlə işləyirdik. Amma bəzən «xam» baytları yazmaq və ya oxumaq lazım olur (məsələn, şəkillər, arxivlər, PDF faylları). Bu halda istifadə edin:

  • Files.readAllBytes(path) — faylı bayt massivinə oxuyur.
  • Files.write(path, byteArray) — bayt massivini fayla yazır.

Nümunə: faylın kopyalanması

import java.nio.file.*;
import java.io.IOException;

public class CopyBinaryFileExample {
    public static void main(String[] args) throws IOException {
        Path source = Paths.get("logo.png");
        Path target = Paths.get("logo_copy.png");

        byte[] data = Files.readAllBytes(source);
        Files.write(target, data);

        System.out.println("Fayl kopyalandı!");
    }
}

Nümunə: binar məlumatların əlavə yazılması

byte[] moreData = new byte[] {1, 2, 3, 4, 5};
Files.write(path, moreData, StandardOpenOption.APPEND, StandardOpenOption.CREATE);

Diqqət: strukturlu məlumat (məsələn, şəkil) saxlayan fayla binar məlumatları əlavə yazmaq adətən faylın korlanmasına səbəb olur. Əlavə yazmadan yalnız mətn faylları və ya xüsusi hazırlanmış binar fayllar (məsələn, loglar) üçün istifadə edin.

5. Axınlar nə vaxt lazımdır (FileInputStream, BufferedReader və s.)

Files.readAllBytes(), Files.write() metodları kiçik və orta ölçülü fayllar üçün rahatdır — bütün məzmunu bir dəfəyə yaddaşa yükləmək mümkündür. Fayl böyükdürsə (məsələn, qiqabaytlarla) və ya faylı sətir-sətir oxumaq istəyirsinizsə (məsələn, logların analizi üçün), axınlardan istifadə edin.

Nümunə: faylı BufferedReader ilə sətir-sətir oxumaq

import java.nio.file.*;
import java.io.*;

public class ReadLinesExample {
    public static void main(String[] args) throws IOException {
        Path path = Paths.get("myfile.txt");

        try (BufferedReader reader = Files.newBufferedReader(path)) {
            String line;
            while ((line = reader.readLine()) != null) {
                System.out.println("Sətir: " + line);
            }
        }
    }
}

Nümunə: fayla BufferedWriter ilə sətir-sətir yazmaq və əlavə yazma

import java.nio.file.*;
import java.io.*;
import java.nio.charset.StandardCharsets;

public class WriteAppendExample {
    public static void main(String[] args) throws IOException {
        Path path = Paths.get("myfile.txt");

        try (BufferedWriter writer = Files.newBufferedWriter(
                path,
                StandardCharsets.UTF_8,
                StandardOpenOption.CREATE,
                StandardOpenOption.APPEND)) {
            writer.write("BufferedWriter ilə daha bir sətir!");
            writer.newLine();
        }
    }
}

6. Təcrübə: fayl yaradırıq, ona sətirlər əlavə yazırıq

Gəlin hamısını bir tətbiqdə birləşdirək. Tutaq ki, mətn faylında tapşırıqlar siyahısı (todo-list) aparan proqramımız var. İstifadəçi hər dəfə yeni tapşırıq əlavə etdikdə, onu faylın sonuna yazırıq.

import java.nio.file.*;
import java.io.IOException;
import java.util.List;
import java.util.Scanner;

public class TodoList {
    public static void main(String[] args) throws IOException {
        Path path = Paths.get("todo.txt");
        Scanner scanner = new Scanner(System.in);

        System.out.print("Yeni tapşırıq daxil edin: ");
        String task = scanner.nextLine();

        // Tapşırığı faylın sonuna əlavə edirik (fayl yoxdursa yaradırıq)
        Files.write(path, 
            List.of(task), 
            StandardOpenOption.CREATE, 
            StandardOpenOption.APPEND);

        System.out.println("Tapşırıq əlavə olundu!");
    }
}

Proqramı bir neçə dəfə işə salın — hər tapşırıq faylda yeni sətirdə görünəcək. Beləcə, ilk «daimi» todo-siyahımız hazırdır!

7. Xətaların emalı: nə səhv gedə bilər?

Fayllarla işləmək həmişə xəta riski daşıyır. Aşağıdakılar baş verə bilər:

  • IOException — bütün giriş-çıxış xətaları üçün əsas istisna. Fayl başqa proqram tərəfindən istifadə olunursa, yazma/oxuma icazələri yoxdursa, disk doludursa və s. hallarda yarana bilər.
  • NoSuchFileException — mövcud olmayan faylı oxumağa və ya əlavə yazmağa cəhd etdikdə (və CREATE seçimini göstərmədikdə).
  • FileAlreadyExistsExceptionCREATE_NEW seçimini istifadə edirsinizsə, amma fayl artıq mövcuddursa.

Tövsiyə: fayllarla işi həmişə try-catch blokuna alın:

try {
    // fayllarla əməliyyatlarınız
} catch (IOException e) {
    System.out.println("Fayl ilə işləyərkən xəta: " + e.getMessage());
}

8. Fayl açma rejimləri ilə işləyərkən tipik səhvlər

Səhv №1: əlavə yazmada CREATE seçimini göstərməyi unutmaq. Əgər hələ mövcud olmayan fayla (APPEND) əlavə yazmağa cəhd etsəniz, NoSuchFileException alacaqsınız. Faylın avtomatik yaradılmasını istəyirsinizsə, həmişə CREATE əlavə edin.

Səhv №2: faylın təsadüfən üzərinə yazılması. Əlavə seçimlər olmadan Files.write(path, data) çağırışı faylın köhnə məzmununu tam silir. Məlumatı əlavə etmək, köhnəni silməmək istəyirsinizsə, APPEND istifadə edin.

Səhv №3: binar məlumatları mətn faylına (və ya əksinə) əlavə yazmağa cəhd. Mətn və binar məlumatları eyni faylda qarışdırmaq çox güman ki, oxunmayan fayla səbəb olacaq. Həmişə bir faylda bir formata sadiq qalın.

Səhv №4: axını bağlamağı unutmaq. Axınlardan (BufferedWriter, BufferedReader) istifadə edirsinizsə, onları bağlamağı unutmayın (ən yaxşısı try-with-resources ilə), əks halda fayl bloklana bilər.

Səhv №5: istisnaları emal etməmək. Fayllarla hər bir əməliyyat IOException ata bilər. Xətanı emal etməsəniz, proqram qəfil dayanacaq.

Şərhlər
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION