CodeGym /Java Blogu /Rastgele /anonim sınıflar
John Squirrels
Seviye
San Francisco

anonim sınıflar

grupta yayınlandı
MERHABA! Bugünün dersinde iç içe sınıflar konusunu incelemeye devam edeceğiz. Şimdi sıra son gruba geldi: anonim iç sınıflar. Diyagramımıza geri dönelim: Anonim sınıflar - 2Geçen derste bahsettiğimiz yerel sınıflar gibi, anonim sınıflar da bir tür iç sınıftır... Ayrıca birçok benzerlikleri ve farklılıkları vardır. Ama önce konuya girelim: neden tam olarak "anonim" olarak adlandırılıyorlar? Bunu cevaplamak için basit bir örnek düşünün. Sürekli çalışan ve bir şeyler yapan temel bir programımız olduğunu hayal edin. Bu program için birkaç modülden oluşan bir izleme sistemi oluşturmak istiyoruz. Bir modül, genel performans göstergelerini izleyecek ve bir günlük tutacaktır. İkincisi, hataları bir hata günlüğüne kaydeder ve kaydeder. Üçüncüsü, şüpheli etkinliği izleyecektir: örneğin, yetkisiz erişim girişimleri ve diğer güvenlikle ilgili şeyler. Üç modülün de özünde basitçe programın başında başlaması ve arka planda çalışması gerektiğinden,

public interface MonitoringSystem {
  
   public void startMonitoring();
}
3 somut sınıf bunu uygulayacak:

public class GeneralIndicatorMonitoringModule implements MonitoringSystem {
   
@Override
   public void startMonitoring() {
       System.out.println("Starting to monitor general indicators!");
   }
}


public class ErrorMonitoringModule implements MonitoringSystem {

   @Override
   public void startMonitoring() {
       System.out.println("Starting to monitor errors!");
   }
}


public class SecurityModule implements MonitoringSystem {

   @Override
   public void startMonitoring() {
       System.out.println("Starting to monitor security!");
   }
}
Görünüşe göre her şey yolunda. Birkaç modülden oluşan oldukça tutarlı bir sistemimiz var. Her birinin kendi davranışı vardır. Yeni modüllere ihtiyaç duyarsak ekleyebiliriz çünkü uygulaması oldukça kolay bir arayüze sahibiz. Ancak izleme sistemimizin nasıl çalışacağını düşünelim. Temel olarak, sadece 3 nesne — , , — Anonim sınıflar - 3oluşturmamız ve her biri için yöntemi çağırmamız gerekiyor. Yani tek yapmamız gereken 3 adet nesne oluşturup üzerlerine 1 adet method çağırmak. GeneralIndicatorMonitoringModuleErrorMonitoringModuleSecurityModulestartMonitoring()

public class Main {

   public static void main(String[] args) {

       GeneralIndicatorMonitoringModule generalModule = new GeneralIndicatorMonitoringModule();
       ErrorMonitoringModule errorModule = new ErrorMonitoringModule();
       SecurityModule securityModule = new SecurityModule();

       generalModule.startMonitoring();
       errorModule.startMonitoring();
       securityModule.startMonitoring();
   }
}
Konsol çıktısı:

Starting to monitor general indicators! 
Starting to monitor errors! 
Starting to monitor security!
Ve bu kadar az çalışma ile tüm sistemi yazdık: 3 sınıf ve bir arayüz! Ve tüm bunlar 6 satır kod elde etmek için. Öte yandan, seçeneklerimiz neler? Bu "tek seferlik" dersleri yazmamız pek hoş değil. Ama bunu nasıl düzeltebiliriz? Burada isimsiz iç sınıflar imdadımıza yetişiyor! İşte bizim durumumuzda nasıl göründükleri:

public class Main {

   public static void main(String[] args) {

       MonitoringSystem generalModule = new MonitoringSystem() {
           @Override
           public void startMonitoring() {
               System.out.println("Starting to monitor general indicators!");
           }
       };

       

MonitoringSystem errorModule = new MonitoringSystem() {
           @Override
           public void startMonitoring() {
               System.out.println("Starting to monitor errors!");
           }
       };

       MonitoringSystem securityModule = new MonitoringSystem() {
           @Override
           public void startMonitoring() {
               System.out.println("Starting to monitor security!");
           }
       };

       generalModule.startMonitoring();
       errorModule.startMonitoring();
       securityModule.startMonitoring();
   }
}
Neler olduğunu anlayalım! Görünüşe göre bir arayüz nesnesi oluşturuyoruz:

MonitoringSystem generalModule = new MonitoringSystem() {
   
@Override
   public void startMonitoring() {
       System.out.println("Starting to monitor general indicators!");
   }
};
Ancak arayüz nesneleri yaratamayacağımızı uzun zamandır biliyoruz! Ve öyle - bu imkansız. Aslında, yaptığımız bu değil. Yazdığımızda:

MonitoringSystem generalModule = new MonitoringSystem() {
   
};
Java makinesinde aşağıdakiler gerçekleşir:
  1. Arabirimi uygulayan adsız bir Java sınıfı oluşturulur MonitoringSystem.
  2. Derleyici böyle bir sınıf gördüğünde, arabirimin tüm yöntemlerini uygulamanızı ister MonitoringSystem(bunu 3 kez yaptık).
  3. Bu sınıfın bir nesnesi oluşturulur. Koda dikkat edin:

MonitoringSystem generalModule = new MonitoringSystem() {
   
};
Sonunda bir noktalı virgül var! Bir nedenden dolayı orada. Eşzamanlı olarak sınıfı bildiririz (küme parantez kullanarak) ve onun bir örneğini yaratırız (kullanarak ();). Üç nesnemizin her biri, startMonitoring()yöntemi kendi yöntemiyle geçersiz kılar. Son olarak, her biri için bu yöntemi basitçe çağırıyoruz:

generalModule.startMonitoring();
errorModule.startMonitoring();
securityModule.startMonitoring();
Konsol çıktısı:

Starting to monitor general indicators! 
Starting to monitor errors! 
Starting to monitor security!
Bu kadar! MonitoringSystemHedefimize ulaştık: üç nesne yarattık , bir yöntemi üç farklı şekilde geçersiz kıldık ve onu üç kez çağırdık. Üç modül de başarıyla çağrıldı ve çalışıyor. Aynı zamanda programımızın yapısı çok daha basit hale geldi! Sonuçta, GeneralIndicatorMonitoringModule, ErrorMonitoringModuleve SecurityModulesınıflar artık programdan tamamen kaldırılabilir! Onlara ihtiyacımız yok - onlarsız harika bir iş çıkardık. Anonim sınıflarımızın her birinin farklı davranışlara ihtiyacı varsa, örneğin diğerlerinin sahip olmadığı kendi özel yöntemlerine, bunları kolayca ekleyebiliriz:

MonitoringSystem generalModule = new MonitoringSystem() {
  
   @Override
   public void startMonitoring() {
       System.out.println("Starting to monitor general indicators!");
   }
  
   public void someSpecificMethod() {

       System.out.println("Specific method only for the first module");
   }
};
Oracle belgeleri iyi bir öneri sunar : "Yerel bir sınıfı yalnızca bir kez kullanmanız gerekiyorsa [anonim sınıfları] kullanın." Anonim bir sınıf, tam teşekküllü bir iç sınıftır. Buna göre, statik ve özel değişkenler dahil olmak üzere harici sınıfın değişkenlerine erişimi vardır:

public class Main {

   private static int currentErrorCount = 23;

   public static void main(String[] args) {

       MonitoringSystem errorModule = new MonitoringSystem() {
          
           @Override
           public void startMonitoring() {
               System.out.println("Starting to monitor errors!");
           }

           public int getCurrentErrorCount() {

               return currentErrorCount;
           }
       };
   }
}
Yerel sınıflarla ortak bir noktaları vardır: yalnızca ilan edildikleri yöntemin içinde görünürler. Yukarıdaki örnekte, errorModuleyöntemin dışında nesneye erişme girişimleri main()başarısız olacaktır. Ve anonim sınıfların "atalarından" (iç sınıflar) miras aldığı bir önemli sınırlama daha vardır: anonim bir sınıf, statik değişkenler ve yöntemler içeremez . Yukarıdaki örnekte, metodu statik yapmaya çalışırsak getCurrentErrorCount(), derleyici bir hata üretecektir:

// Error! Inner classes cannot have static declarations
public static int getCurrentErrorCount() {

   return currentErrorCount;
}
Statik bir değişken bildirmeye çalışırsak aynı sonucu alırız:

MonitoringSystem errorModule = new MonitoringSystem() {

   // Error! Inner classes cannot have static declarations!
   static int staticInt = 10;

   @Override
   public void startMonitoring() {
       System.out.println("Starting to monitor errors!");
   }

};
Ve bugünkü dersimiz sona erdi! Ancak iç içe geçmiş sınıfların son grubunu incelemiş olsak da bu konuyu henüz bitirmedik. İç içe sınıflar hakkında başka ne öğreneceğiz? Kesinlikle yakında öğreneceksiniz! :)
Yorumlar
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION