Bu şekilde yazılmış çoğu değişmez POJO'yu görüyorum:
public class MyObject {
private final String foo;
private final int bar;
public MyObject(String foo, int bar) {
this.foo = foo;
this.bar = bar;
}
public String getFoo() {
return foo;
}
public int getBar() {
return bar;
}
}
Yine de onları bu şekilde yazmaya meyilliyim:
public class MyObject {
public final String foo;
public final int bar;
public MyObject(String foo, int bar) {
this.foo = foo;
this.bar = bar;
}
}
Referansların nihai olduğuna dikkat edin, bu nedenle Nesne hala değişmez. Daha az kod yazmama izin veriyor ve daha kısa (5 karakter: getve ()) erişimine izin veriyor .
Görebildiğim tek dezavantaj getFoo(), çılgınca bir şey yapmak için yolun aşağısındaki uygulamasını değiştirmek isteyip istemediğinizdir . Fakat gerçekçi olarak, bu asla gerçekleşmez, çünkü Nesne değişmezdir; örnekleme sırasında doğrulayabilir, örnekleme sırasında değişmez savunma kopyaları oluşturabilir ( ImmutableListörneğin Guava'nın bakınız ) ve fooveya barnesneye getçağrı için hazır olun .
Kaybettiğim herhangi bir dezavantaj var mı?
DÜZENLE
Sanırım eksik olduğum başka bir dezavantaj ise getveya ile başlayan yöntemlere yansıma kullanan serileştirme kütüphaneleri is, ama bu oldukça korkunç bir uygulama ...
String, intya MyObject. İlk versiyonda, finalsadece sınıf içindeki yapıcıdan başka yöntemlerin denenmemesini sağlamaktır bar = 7;. İkinci versiyonda, finalyapmaktan tüketicilerin önlemek için gereklidir: MyObject x = new MyObject("hi", 5); x.bar = 7;.
Objecthala değişken değil. " Yanıltıcıdır - öyle görünüyor ki herhangi final Objectbirinin değişmez olduğunu düşünüyorsunuz , ki bu değil. Yanlış anlaşılma için üzgünüm.
myObj.getFoo().setFrob(...).
finaldeğişkeni nesneyi değişmez yapmaz. Normaldefinalgeri arama oluşturmadan önce alanları tanımladığım bir tasarım kullanıyorum, böylece geri arama bu alanlara erişebiliyor. Elbette, herhangi birsetXyöntem dahil tüm yöntemleri çağırabilir .