Java Dersleri 9 – Dosya Okuma/Yazma İşlemleri

Bu derste sizlere Java’nın dosya işlemlerinden bahsedeceğim. Üç bölümlük serinin ilkinde genel dosya girdi çıktı mekanizmasından bahsedip metin dosyalarını nasıl okuyup yazabileceğimize bakacağız. Java’da üm girdi çıktı işlemleri, bu dosya olabilir, network soketi olabilir, Stream (akım) sııfları vasıtasıyla gerçekleştirilir. Stream sınıflarını içerisinden veri akan yollar şeklinde düşünebilirsiniz. Bu sınıflar içerisindeki verilere ve buffering (tamponlama) vs gibi özelliklerine göre birbirlerinden ayrılırlar. Genel olarak taşıdıkları verilere göre üçe ayrılırlar:

  1. İkilik Veri Akımları (Byte Streams) : İkili tipteki dosyaları okuyup yazmakta kullanılırlar
  2. Karakter Akımları(Char Streams): Metin belgeleri okuyup yazmakta kullanılırlar
  3. Nesne Akımları(Object streams): Serializable olan Java nesnelerini okuyup  yazmakta kullanılırlar

Bu sınıfların dışında akım sınıflarının özelliklerini değiştiren sarmalayıcı akım sınıfları da mevcuttur. Örneğin BufferedReader sınıfı herhangi bir Reader sınıfını sarmalayarak tamponlama özelliği katar.

İlk olarak karakter akımlarını incelemeye çalışalım. Yazılım geliştirme sürecince çokça karşımıza çıkan metin dosyalarını Java’da okumak için Reader soyut sınıfından türeyen InputStreamReader alt sınıfı olan FileReader sınıfı kullanılır. Dosyaya yazmak için ise API’de bu sınıfın muadili FileWriter sınıfı mevcuttur. Örnek olarak herhangi bir metin dosyasının satır başlarına satır numarasını ekleyen şu kod satırlarını inceleyelim:

    FileWriter fw = null;
                try {
                    int lineNumber = 1;
                    FileReader fr = new FileReader(fileName);
                    fw = new FileWriter("linenumber.txt");

                    int c = fr.read();
                    do {
                        if ((char) c == '\n') {
                            lineNumber++;
                            fw.write(c);
                            fw.write( Integer.toString(lineNumber));
                        }
                        else
                        {
                            fw.write(c);
                        }

                        c  = fr.read();
                    } while (c != -1);

                } catch (IOException ex) {
                    Logger.getLogger(FileIOUI.class.getName()).log(Level.SEVERE, null, ex);
                } finally {
                    try {
                        fw.close();
                    } catch (IOException ex) {
                        Logger.getLogger(FileIOUI.class.getName()).log(Level.SEVERE, null, ex);
                    }
                }

Metin dosyamızı okumak için FileReader sınıfını kullandık. Öncelikle okumak istediğimiz dosya adını kullanarak bir FileReader nesnesi oluşturup, bu nesne üzerinde read() metodunu çağırdık. Bu sınıfın dosyadan okumak için birden fazla metodu bulunmakla beraber burada dosyayı karakter-karakter okumamızı sağlayan int dönüş değerine sahip olan read() metodunu kullandık. Bu metodun dışarıya verdiği int tipindeki değişken aslında char tipinde bir değişken olduğundan tür dönüşüm operatörünü uygulamamızda bir sakınca yoktur yani :

 int c = fr.read();
 if ((char) c == '\n') {
}

kullanımı doğrudur. Burada son olarak dikkat etmemiz gereken husus read() metodunun dosya sonuna geldiğinde değer olarak -1 döndürmesidir. Yani dosya sonuna gelip gelmediğimizi dönüş değerinin -1 olup olmadığını kontrol ederek anlayabiliriz.

Metin dosyası yazmak için ise FileWriter sınıfını kullandık. Yine bu sınıfta da dosyaya yazmak için birden fazla metod bulmak mümkün. Biz burada yine karakter-karakter yazmamıza olanak sağlayan write(int) metodunu kullandık. Sadece satır başlarına yazdırmak isediğimiz satır sayısını String tipine dönüştürüp write(String) metodunu kullanarak dosyaya yazdık. Bu iki farklı kullanımı gösterirsek :

int c = fr.read();
if ((char) c == '\n')
{
	lineNumber++;
        fw.write(c);
        fw.write( Integer.toString(lineNumber));
}

Eğer dosyaya en baştan değil sonuna ekleme yapmak istiyorsak FileWriter sınıfının :

 public FileWriter(File file, boolean append)

yapıcı metodunu kullanabiliriz. Burada ikinci parametreye true değerini vererek dosyaya ekleme yapmak istediğimizi bildirmeliyiz.

Metin dosyalarını işlerken genellikle karakter-karakter okuma/yazma yerine kelime-kelime okuma/yazma yada satır okuma/yazma işlemlerini kullanırız. FileReader ve FileWriter sınıfları bu yeteneklere sahip değildir dolayısıyla bunun için sarmalayıcı sınıflar mevcuttur. Bu sınıfları ve yeteneklerini bir sonraki derste anlatacağım.

Java Dersleri 8 – İç, Gömülü ve İsimsiz Sınıflar (Inner, Nested and Anonymous Classes)

Bu dersimizde Java’nın gömülü sınıf yapısını öğreneceğiz. Java programlama dili kullanıcıya bir sınıf içerisinde başka bir sınıf tanımlama olanağı sağlar. Bu tür sınıflara Gömülü Sınıf (Nested Class) adı verilir. Gömülü sınıflar statik ve statik olmayan gömülü sınıflar olmak üzere ikiye ayrılırlar. Statik olmayan gömülü sınıflara İç Sınıf(Inner Class) adı verilir. Gömülü sınıfların üç temel faydası vardır. Bunlar :

  1. Sınıfların Mantıksal Gruplanması : Ortak iş yapan sınıfların bir arada bulunmasını sağlayarak daha sağlıklı API’ler oluşturmanızı sağlar
  2. Daha İyi Kapsülleme : Sınıf değişkenlerinin private kalmasını sağlayarak daha iyi kapsülleme sağlar
  3. Kod Okunabilirliği : Üst seviye sınıflar altında iş gören gömülü sınıflar kod okunabilirliğini arttırır.

Gömülü sınıf hiyerarşisi aynı zamanda arayüzler için de geçerlidir. Yani arayüzlerde birbirleri içerisinde tanımlanabilirler. Java JDK içerisinde gömülü sınıf kullanımına örnek olabilircek çok sayıda sınıf ve arayüz vardır. Bunlardan bir tanesini inceleyelim :

//üst seviye arayüz tanımı
public interface Map<K ,V> {
int size();
boolean isEmpty();
boolean containsKey(Object key);
boolean containsValue(Object value);
V get(Object key);
V put(K key, V value);
V remove(Object key);
void putAll(Map<? extends K, ? extends V>m);
void clear();
Set<K> keySet();
Collection<V> values();

//gömülü arayüze referans var
Set<Map.Entry<K, V>>; entrySet();

//gömülü arayüz tanımı
interface Entry<K ,V>
{
K getKey();
V getValue();
V setValue(V value);
boolean equals(Object o);
int hashCode();
}

boolean equals(Object o);
int hashCode();
}

Örnekte görüldüğü üzere Map arayüzünün altında Entry gömülü arayüzü tanımlanmış ve

//gömülü arayüze referans var
Set<Map.Entry<K, V>>entrySet();

metod imzasında gömülü arayüz kullanılmıştır. Bu kullanımdan yola çıkarak gömülü arayüz/sınıf tanımlarına nasıl ulaşabiliriz onu görelim. Burada yine statik gömülü sınıflar ve iç sınıflar arasında ayrım yapmalıyız. Statik gömülü sınıftan bir nesne oluşturmak istiyorsak :

ÜstSeviyeSınıf.StatikGömülüSınıf  s  = new ÜstSeviyeSınıf.StatikGömülüSınıf();

Statik gömülü sınıftan bir nesne oluşturmak için üst seviye sınıftan nesne oluşturmamıza gerek yoktur. Oysa ki iç sınıflar üst seviye sınıf olmadan oluşturulamazlar. Yani statik olmayan iç sınıfların varlığı üst seviye sınıfa bağlıdır. Herhangi bir iç sınıfdan nesne oluşturmak için ise :

ÜstSeviyeSınıf s = new ÜstSeviyeSınıf();
ÜstSeviyeSınıf.İçSınıf i = s.new İçSınıf();

Burada en çok dikkat etmemiz gereken kullanım s.new kullanımıdır.

Sınıf tanımı veya herhangi bir metod tanımı içinde isim vermeden yeni bir sınıf tanımı yapılabilir. Bu şekilde tanımlanan sınıflara isimsiz (anonymous) sınıflar denir.  İsimsiz sınıflar sadece tanımlandıkları yerde kullanılırlar.  En klasik kullanım alanları …Listener (ActionListener,MouseMotionListener vs) gerçeklemeleridir. Örneğin NetBeans tarafından düğme kontrolü için üretilen kodları inceleyelim :


jButton1.addActionListener(new java.awt.event.ActionListener() {
public void actionPerformed(java.awt.event.ActionEvent evt) {
jButton1ActionPerformed(evt);
}
});

Burada addActionLisener metodu parametre olarak ActionListener arayüzünü gerçekleyen bir nesne alır.  Bu nesne isimsiz olarak tanımlanıp ActionListener’da gerçeklenmesi gereken actionPerformed metodunu içerir. Görüldüğü gibi sadece sınıf tanımı yapılıp sınıfa herhangi bir isim verilmemiştir.  İsimsiz sınıf tanımlama sentaksı


new Sınıfİsmi/Arayüzİsmi () {}

şeklindedir. Eğer Sınıfİsmi verilmişse isimsiz sınıf bu sınıftan türer. Eğer Arayüzİsmi verilmişse isimsiz sınıf bu arayüzü gerçekler.

Java Dersleri 7 – Çok Biçimlilik (Polymorphism)

Bu dersimizde Java’nın nesne odaklı programlamanın olmazsa olmazlarından çok biçimliliği nasıl gerçeklediğini öğreneceğiz. Çok biçimlilik aynı tip değişken üzerinden birbirinden farklı davranışlar elde etme tekniğidir. Programlama dillerinin dinamik bağlama (dynamic binding) yada koşum zamanı bağlama (runtime binding) özelliğinden faydalanılarak hayata geçirilir. Tabiki dinamik bağlamadan yararlanabilme için metod ezme (method overriding) tekniğini bilmemiz gerekiyor. Öncelikle bahsettiğimiz terimleri örneklerle açıklayalım. Metod ezme işlemi kalıtım esnasında ana sınıfta halihazırda tanımlı olan methodu yeniden yazarak ana sınıftaki metodu geçersiz kılma işlemidir. Örneğin :
(daha fazla…)

Java Dersleri 6 – Arayüzler ve Gerçeklenmesi (Interface and Implementation)

Nesne odaklı programlamada arayüzler sınıfların dış dünyaya açılan kapılarıdır. Bir başka deyimle arayüzler sınıflar arası iletişimde imzalanan kontratlardır. Bir arayüzü gerçekleyen sınıf o arayüze ait metodların tamamını gerçeklemek zorundadır. Java prensip olarak çoklu mirası desteklememektedir. Bunun yerine ise çoklu arayüzleri gerçekleme imkanı sağlamıştır. Arayüzleri tanımlamak için “interface” anahtar kelimesi kullanılır.
(daha fazla…)

Java Dersleri 5 – Kalıtım (Inheritance)

Bu derste Java’nın nesne yönelimli programlamanın temeli olan kalıtım(Inheritance) kavramını nasıl gerçeklediğini öğreneceğiz. Yazılım terminolojisinde kalıtım bir sınıfın diğer bir sınıfın özelliklerini belirli kısıtlar çerçevesinde kazanmasıdır. Aynı kod parçalarının tekrar tekrar yazılmasını engellemenin yanı sıra nesneler arasında gerçek hayata benzer mantiki bağlar kurulmasını
kolaylaştırır. Kalıtımın gerçeklenmesini sağlayan anahtar kelime “extends” dir. Örneğin :
(daha fazla…)

Java Dersleri 4 – Erişim Denetleyicileri (Access Modifiers)

Java Dersleri 4

Java Dersleri 4


Bu dersimizde Java’nın metodlar ve sınıflar üzerinde erişim kurallarını düzenleyen anahtar kelimelerini ve nasıl kullanıldıklarını örnekleriyle öğreneceğiz. Java’da dört adet erişim düzeyi bulunmakla birlikte üç adet erişim denetleyici anahtar kelime vardır. Dördüncü erişim düzeyi ise bu kelimelerin bulunmadiği seviyedir. Erişim kontrolü yazılımda her birimin kendi işine odaklanmasına yardımcı olur. Temelde nesne yönelimli programanın ana unsrlarındandır. Veri kapsülleme, miras ve çok biçimlilik paradigmalarının hayata geçirilmesine olanak tanırlar. Java’da erişim denetleyici anahtar kelimeler şunlardır:

1)Public
2)Protected
3)Private

(daha fazla…)

Java Dersleri 3 – Kontrol Yapıları

Java Dersleri 3

Java Dersleri 3


Bu dersimizde Java’nın kodun akışına yön veren kontrol ifadelerinin kullanımını öğreneceğiz. Java kontrol ifadeleri
temel olarak şunlardan oluşmaktadır:

1)if-else if – else blokları
2)for ve foreach döngüleri
3)while ve do-while döngüleri
4)switch-case blokları

Şimdi sırasıyla bunları örneklerle açıklayalım.
(daha fazla…)

  • Sayfa 1 - 2
  • 1
  • 2
  • >