Java yöntemi adı ne zaman çok uzun? [kapalı]


173

Son haftalarda bir Yöntem veya Sınıf (50 karakter) için gerçekten uzun isimler kullanan bazı adamlar gördüm, bu genellikle okunabilirliği geliştirdiği öncülünde, bence bu gibi uzun bir isim olduğumuzun bir göstergesi böyle uzun bir isme ihtiyacımız olursa bir yöntem sınıfında çok fazla veya çok şey yapmaya çalışıyorum, ancak bunun hakkında ne düşündüğünüzü bilmek istedim.

Bir örnek:

getNumberOfSkinCareEligibleItemsWithinTransaction

19
EVET bu bir "kod kokusu" ... c2.com/cgi/wiki?LongMethodSmell
Dan Rosenstark

23
666 karakterden uzun olduğunda bir sorun olduğunu bilirsiniz.
Thomas Eding

8
Örneğinizde @yar, "Uzun Yöntem" in tam tersi, iyi bir şey olarak kabul edilen "Kısa Yöntem" dir. Bu yüzden açıkça yöntem adına atıfta bulunmuyor; kod satırlarına atıfta bulunuyor (ya da benzer bir şey). örneğin, f()çok kısa bir işlev, ama kesinlikle iyi bir uygulama değil ... ve orada bazı programlama matematikçilerine söylemelisiniz bir şey :)
sfussenegger

3
@sfussenegger, bu doğru. Ancak yöntem adı uzunluğu ile yöntem uzunluğu arasındaki korelasyon üzerine bahse girerim. f()büyük bir işlev olmayabilir, ancak bu $()adam Javascript yöntemi dünyasında bir rock yıldızı gibidir.
Dan Rosenstark

7
@yar, verdiğiniz bağlantı, yöntem adının uzunluğuna değil, yöntemin satır uzunluğuna değinmiştir .
Thorbjørn Ravn Andersen

Yanıtlar:


398

Java'daki bir ad veya başka bir dil, yöntemin davranışını eşit olarak ileten daha kısa bir ad olduğunda çok uzun olur.


65
Matematiksel olarak zarif.
Ricket

304
Yani, örneğin, boolean doesShorterNameExistThatEquallyConvaysTheBehaviorOfTheMethod(String s)yeniden düzenlenmesi gerekir boolean isTooLong(String s).
z5h

6
Sadece davranışı iletmekle kalmayıp aynı zamanda projenin ve dilin konvansiyonunu sürdürmek istediğiniz için de aynı fikirde değilim. Yani Python'da söyleyebilirsiniz eligible_items_cntama Java'da genellikle söylersiniz getEligibleItemsCount.
flybywire

17
@flybywire: Aşırı uzun isimler yazmanızı sağlayan herhangi bir sözleşme şüpheli bir fayda sağlar.
MAK

20
@MAK @ S.Lott Ne hakkında getLength()vs. length()? 'Get' veya 'set' yazdıktan sonra otomatik tamamlamalara bakmayı çok seviyorum - bu durumda kısaltma yerine kısalmayı tercih ederim.
sfussenegger

202

Yöntem adlarının uzunluğunu azaltmak için bazı teknikler:

  1. Tüm programınız, sınıfınız veya modülünüz 'cilt bakım ürünleri' ile ilgiliyse, cilt bakımını bırakabilirsiniz. Örneğin, sınıfınız çağrıldığında SkinCareUtils,getNumberOfEligibleItemsWithinTransaction

  2. Değişebilirsin içinde için de ,getNumberOfEligibleItemsInTransaction

  3. İşlemi sizi Tx olarak değiştirebilirsiniz getNumberOfEligibleItemsInTx.

  4. Veya yöntem bir tür parametresini kabul ederse Transaction, InTx'i tamamen bırakabilirsiniz:getNumberOfEligibleItems

  5. NumberOf değerini sayıma göre değiştirirsiniz: getEligibleItemsCount

Şimdi bu çok makul. Ve% 60 daha kısadır.


11
ilave olarak, 5) verecek getEligibleItems()ve getEligibleItemsCount()), örneğin otomatik tamamlama veya javadoc (alfabetik listelerinde birbirine
sfussenegger

4
Ve genellikle doğru olduğu gibi, daha kısa isim haiku kuralına uyuyor.
sal

2
@mercator countEligibleItems gibi getEligibleItems gibi standart bir kural kullanmak ifadede belirsizlik olasılığını azaltır. Yöntemin ne yapması gerektiği konusunda daha az belirsiz olan, okunabilirliği artırır. Yönteme daha fazla bakmadan, "sayan" bir yöntem, "elde edilen" bir yöntemin uzun vadede neyi başardığından daha az açıktır.
Bill

53
Ben gibi kısalt sevmediğim Tx, Cnt, grphve böylece (Btw üzerine ... Tx"İletim" veya "verici" kısaltmasıdır)
Meinersbur

14
Evet, "Tx" i kullanmaya karar verene kadar seninle aynı fikirdeydim.
Ponkadoodle

183

Sadece bir değişiklik için, öznel olmayan bir cevap: 65536 karakter.

A.java:1: "xxxxxxxxxxxxxxxxxxxx ..." dizesi için UTF8 gösterimi sabit havuz için çok uzun

;-)


4
evet çok uzun zaman JVM hiçbir mo ele koyamaz :)
Anurag

35
İçin 1 literal cevap.
sal

37
Teknik olarak, Java dil spesifikasyonunun tanımlayıcı uzunluğu için bir üst sınırı yoktur. Bu, JVM uygulamanızın bir sınırlamasıdır. Şerefe!
uckelman

13
Sun'ın derleyicisi görünüşe uygun değil. java.sun.com/docs/books/jls/third_edition/html/lexical.html#3.8 diyor ki: "Bir tanımlayıcı sınırsız uzunluktaki bir dizidir ..."
Michael Myers

6
JVM spektrumu etmez hata mesajı işaret ettiği gibi, bir üst sınırı vardır. Utf8'lerin sabit havuz gösterimi burada belirtilen 2 ^ 16 bayt ile sınırlıdır . Sınıf adları ve yöntem adları sabit havuzda utf8 olarak depolanmalıdır.
thejoshwolfe

42

Herkese katılıyorum: yöntem adları çok uzun olmamalıdır. Yine de bir istisna eklemek istiyorum:

Bununla birlikte, JUnit test yöntemlerinin isimleri uzun olabilir ve cümlelere benzemelidir.

Neden?

  • Çünkü başka bir kodda çağrılmazlar.
  • Çünkü test ismi olarak kullanılırlar.
  • Çünkü daha sonra gereksinimleri açıklayan cümleler olarak yazılabilirler. (Örneğin, AgileDox kullanarak )

Misal:

    @Test
    public void testDialogClosesDownWhenTheRedButtonIsPressedTwice() {
        ...
    }

Bu fikir hakkında daha fazla bilgi için bkz. " Davranış Odaklı Tasarım ".


5
+1 Buna katılıyorum ve yaptığım da bu, JUnit 4 yöntemlerinin testartık başlaması gerekmese de, bu da kullanma olasılığını açıyor should: gibi dialogShouldCloseWhenTheRedButtonIsPressedTwice(). Yoksa Test sınıfını çağırabilir DialogShouldve daha sonra yöntem closeWhenTheRedButtonIsPressedTwice()bu yüzden onları bir arada okumak,: DialogShould.closeWhenTheRedButtonIsPressedTwice().
stivlo

Kabul ederken, aynı zamanda çok uzun bir cümlenin çok fazla iş yapan bir test önerebileceğini de öneririm!
Brian Agnew

17

"... WithinTransaction" bağlamı açık olmalıdır. Nesne yönelimi bununla ilgilidir.

Yöntem bir sınıfın parçasıdır. Sınıf "İşlem" anlamına gelmiyorsa - ve sizi her zaman "İçeriden İşlem" demek zorunda kalmazsa, sorunlarınız olur.


2
Bir çeşit işlem parametresi de alabilir
willcodejavaforfood

3
Yukarıdaki en iyi skorlama yanıtından da anlaşılacağı gibi, OO tavsiyesi yerine taşra basitliği için gidin. +1
Dan Rosenstark

@yar İnsanlar asla yanlış değildir.
CurtainDog

12

Haiku kuralını isimler için kullanma eğilimindeyim :

 Seven syllable class names 
 five for variables
 seven for method and other names

Bunlar maksimum adlar için temel kurallardır. Bunu sadece okunabilirliği geliştirdiğinde ihlal ediyorum. RecalculateMortgageInterest (currentRate, quoteSet ...) gibi bir şey, recalculateMortgageInterestRate veya recalculateMortgageInterestRateFromSet öğelerini, javadoc veya .NET eşdeğeri gibi katıştırılmış dokümanlardan oldukça açık olması gerektiğinden recalculateMortgageInterestRate veya recalculateMortgageInterestRateFromSet'ten daha iyidir.

NOT: Gerçek bir haiku değil, 5-7-5 yerine 7-5-7. Ama yine de buna haiku demeyi tercih ediyorum.


13
Sınıflar yedi, beşten az değişkenler, geri kalanı için yedi
James

8
"değişkenler en fazla beş" (beşten az doğru değil)
Jason S

Küçük isimler kodların daha az okunmasına neden olabilir.
Deniss M.

10

Java, belki de IDE'lerin iyi otomatik tamamlama ile geldikleri için uzun isimleri teşvik etme kültürüne sahiptir.

Bu site , JRE'deki en uzun sınıf adının InternalFrameInternalFrameTitlePaneInternalFrameTitlePaneMaximizeButtonWindowNotFocusedState92 karakter uzunluğunda olduğunu söylüyor .

En uzun yöntem adına gelince supportsDataDefinitionAndDataManipulationTransactions, 52 karakter olan bir tane buldum .


20
Görünüşe göre bu sınıf, Yedek İşleri Dairesi Başkanlığı tarafından İşten Ayrılma Dairesi Başkanlığı'nda işleri isimlendiren insanlar tarafından adlandırılmış gibi görünüyor.
Michael Madsen

1
@MichaelMadsen: Gerçekten gereksiz mi, yoksa başka bir çerçevenin içine yerleştirilmiş bir çerçeveyi mi tanımlıyor?
endolith

PEP-8 bu sınıf adına sahip bir kelime ister.
Mateen Ulhaq

9

Küçük bir kelime asla uzun bir kelime kullanmaz.

"Yöntem adının uzunluğu yöntem uzunluğuyla orantılı" tezinizin gerçekten su tuttuğunu sanmıyorum.

Verdiğiniz örneği alın: "getNumberOfSkinCareEligibleItemsWithinTransaction". Bu bana sadece bir şey yaptığı gibi geliyor: bir işlemdeki belirli bir kategoriye giren öğelerin sayısını sayar. Tabii ki yöntemin gerçek kodunu görmeden yargılayamıyorum, ama bu benim için iyi bir yöntem gibi geliyor.

Öte yandan, "processSale" veya popüler olan "doStuff" gibi çok işe yarayan çok kısa ve özlü isimlere sahip birçok yöntem gördüm.

Yöntem adı uzunluğu hakkında zor ve hızlı bir kural vermek zor olacağını düşünüyorum, ancak amaç şöyle olmalıdır: fonksiyonun ne yaptığını iletecek kadar uzun, okunabilir olacak kadar kısa. Bu örnekte, "getSkinCareCount" muhtemelen yeterli olacağını düşünürdüm. Soru, ayırt etmeniz gereken şey. İşlemlerde cilt bakımı için uygun öğeleri sayan bir işleviniz ve başka bir şeydeki cilt bakımı için uygun öğeleri sayan başka bir işleviniz varsa, "withinTransactions" değer katar. Ancak, bir işlemin dışındaki bu tür öğeler hakkında konuşmak için bir şey ifade etmiyorsa, adı bu kadar gereksiz bilgilerle karıştırmanın bir anlamı yoktur.

İkincisi, bence herhangi bir yönetilebilir uzunlukta bir adın, işlevin en önemsiz durumlar hariç tümünde tam olarak ne yaptığını söyleyeceğini varsaymak çok gerçekçi değil. Gerçekçi bir hedef, okuyucuya ipucu veren ve daha sonra hatırlanabilecek bir isim yapmaktır. Örneğin, çözgü hızına ulaşmak için ne kadar antimadde tüketmemiz gerektiğini hesaplayan kodu bulmaya çalışıyorsam, işlev adlarına bakar ve "calibrateTransporter", "firePhasers" ve "calcAntimatterBurn" ifadelerini görürsem, ilk ikisi değil ama üçüncüsü olabilir. Gerçekten aradığım kişi olup olmadığını kontrol edip bulursam, bu sorun üzerinde çalışmak için yarın geri döndüğümde biraz daha hatırlamak kolay olacaktır. Yeteri kadar iyi.

Benzer üç, uzun isimler kısa isimlerden daha kafa karıştırıcıdır. "CalcSalesmanPay" ve "calcGeekPay" adında iki fonksiyonum varsa, hızlı bir bakışta iyi bir tahmin yapabilirim. Ancak "calculateMonthlyCheckAmountForSalesmanForExportToAccountingSystemAndReconciliation" ve "calculateMonthlyCheckAmountForProgrammersForExportToAccountingSystemAndReconciliation" olarak adlandırılırlarsa, hangilerinin hangisi olduğunu görmek için adları incelemeliyim. İsimdeki ekstra bilgi, bu gibi durumlarda muhtemelen tersine verimlidir. Yarım saniyelik bir düşünceyi 30 saniyelik bir düşünceye dönüştürür.


Acı çeken bu zayıf cevap için +1.
Dan Rosenstark

7

Arayüzünüzü istediğiniz gibi tasarlayın ve uygulamanın eşleşmesini sağlayın.

Örneğin, belki bunu şöyle yazardım

getTransaction().getItems(SKIN_CARE).getEligible().size()

veya Java 8 akışlarıyla:

getTransaction().getItems().stream()
    .filter(item -> item.getType() == SKIN_CARE)
    .filter(item -> item.isEligible())
    .count();

6

Kuralım şöyledir: bir ad kendi satırında görünecek kadar uzunsa, o zaman çok uzundur. (Pratikte, bu nadiren 20 karakterin üzerindeyim demektir.)

Bu, görünür dikey kod satırı sayısının kodlama hızı / etkinliği ile pozitif korelasyon gösterdiğini gösteren araştırmalara dayanmaktadır. Sınıf / yöntem adları bunu önemli ölçüde incitmeye başlarsa, çok uzundur.

Yöntem / sınıfın bildirildiği bir yorum ekleyin ve bunun ne olduğuna ilişkin uzun bir açıklama istiyorsanız IDE'nin sizi oraya götürmesine izin verin.


Bunun gibi kuralları severim. Sizin / ekibinizin onları rastgele oluşturduğunu aklınızda bulundurduğunuz sürece, hepsi iyi. Öte yandan, bunu değerlendiremiyorum çünkü "araştırma gösteren" bu araştırmayla ilgili bir bağlantıya ya da onunla ilgili bir şeye ihtiyaç duyacaktır ...
Dan Rosenstark

5

Yöntemin kendisi muhtemelen çok fazla iş yapıp yapmadığının daha iyi bir göstergesidir ve bu bile size sadece kaba bir fikir verir. Özlü olmak için çabalamalısınız, ancak tanımlayıcılık daha önemlidir. Aynı anlamı daha kısa bir adla aktaramazsanız, adın kendisi muhtemelen iyidir.


3

Bir dahaki sefere bir yöntem adı yazacaksanız, sadece aşağıdaki alıntıyı düşünün

"The man who is going to maintain your code is a phyco who knows where you stay"

13
İyi bir şey, o sadece bir deniz yosunu ve bir 'psiko' değil
StingyJack

2

Bu yöntem adı kesinlikle çok uzun. Böyle büyüklükteki yöntem adlarını okurken aklım dolaşıyor. Boşluksuz bir cümleyi okumak gibi.

Şahsen, yöntemlerde mümkün olduğunca az kelime tercih ediyorum. Paket ve sınıf adının anlam ifade edip etmediği size yardımcı olur. Sınıfın sorumluluğu çok özlü ise , dev bir yöntem adına gerek yoktur. Orada neden "WithinTransaction" ı merak ediyorum.

"getNumberOfSkinCareEligibleItemsWithinTransaction" şunlar olabilir:

com.mycompany.app.product.SkinCareQuery.getNumEligibleItems ();

Sonra kullanımda, yöntem "query.getNumEligibleItems ()" gibi görünebilir


2

Bir değişken adı, daha kısa bir ad, tüm program veya programın önemli bölümleri üzerinde daha iyi kod okunabilirliğine izin verdiğinde çok uzundur.

Daha uzun bir ad, bir değer hakkında daha fazla bilgi aktarmanıza izin veriyorsa. Ancak, bir ad çok uzunsa, kodu karmaşıklaştıracak ve kodun geri kalanını anlama yeteneğini azaltacaktır. Bu genellikle satır kaydırmasına neden olarak ve diğer kod satırlarını sayfa dışına iterek olur.

Hangisi daha iyi okunabilirlik sunacağını belirliyor. Değişken, kısa bir alanda sık sık veya birkaç kez kullanılıyorsa, ona kısa bir ad vermek ve açıklığa kavuşturmak için daha iyi olabilir. Okuyucu yoruma kolayca geri dönebilir. Değişken, program boyunca sık sık, genellikle parametre olarak veya diğer karmaşık işlemlerde kullanılıyorsa, adı kısaltmak veya kısaltmaları okuyucuya hatırlatma olarak kullanmak en iyisi olabilir. Anlamını unuturlarsa, her zaman değişken bildirimiyle bir yoruma başvurabilirler.

Bu, kod okuyucunun neyi anlamaya çalıştığını düşünmeniz ve kodun zaman içinde nasıl değişeceğini ve büyüyeceğini dikkate almanız gerektiğinden, bunu yapmak kolay bir işlem değildir. Bu yüzden şeyleri adlandırmak zor.

Okunabilirlik, i'nin DescriptiveLoopCounterName yerine döngü sayacı olarak kullanılmasının neden kabul edilebilir olduğudur. Bu bir değişken için en yaygın kullanım olduğundan, neden var olduğunu açıklayan en az ekran alanı harcayabilirsiniz. Uzun ad, döngü koşulunu nasıl test ettiğinizi veya bir diziye dizine eklediğinizi anlamayı zorlaştırarak zaman kaybına neden olur.

Spektrumun diğer ucunda, bir işlev veya değişken, çok parametreli bir işlev çağrısına geçirilmesi gibi karmaşık bir işlemde nadiren kullanılırsa, ona aşırı açıklayıcı bir ad vermeyi göze alabilirsiniz.



1

İyi cevapların bir kombinasyonunu kullanın ve makul olun.

Yöntemin ne yaptığını tamamen, açık ve net bir şekilde tarif edin.

Yöntem adı çok uzun görünüyorsa - yeniden yapmak için yöntemi yeniden düzenleyin.


1

Yöntemin adı başka bir satıra sarıldığında ve yönteme çağrı satırdaki tek şey olduğunda ve kenar boşluğuna oldukça yakın olduğunda çok uzun olur. Kullanacak kişilerin ekranının ortalama boyutunu dikkate almalısınız.

Fakat! İsim çok uzun görünüyorsa, muhtemelen çok uzundur. Bu sorunu aşmanın yolu, kodunuzu bir bağlam dahilinde olacak şekilde yazmanız ve ad kısa ama diğer bağlamlarda çoğaltılmasıdır. Bu, birisinin tam adı yerine İngilizce "o" veya "o" diyebileceğiniz zaman gibidir.


1

Bir şeyin ne hakkında olduğunu ayrıntılarıyla açıkladığı zaman çok uzun.

Örneğin, bu adlar işlevsel olarak eşdeğerdir.

Java dilinde: java.sql.SQLIntegrityConstraintViolationException

Python / Django'da: django.db.IntegrityError

Kendinize bir SQL / db paketinde kaç tane daha bütünlük hatası ortaya çıkarabileceğinizi sorun. ;) Dolayısıyla db.IntegrityErroryeterlidir.


Her zaman tersini tartışabilirsiniz. Söz konusu şeyin ne ile ilgili olduğunu ayrıntılı bir şekilde açıkladığında, yöntemin başka ne yaptığı açıktır, karışıklığa neden olabilir ve yöntemin yanlış kullanılmasına neden olabilir.
Jonas Geiregat

0

Tanımlayıcı adı, Java derleyicinizin işleyebileceği uzunluğu aştığında çok uzun.


3
Ne?! Bunun için neden reddedildiğimi anlamıyorum. Soru gerekli bir koşulu sormadı, sadece yeterli bir durum!
uckelman

0

Burada iki yol veya bakış açısı vardır: Birincisi, yöntemin ne yaptığını açıklamak için mümkün olduğunca açıklayıcı olduğu sürece, yöntem adının ne kadar uzun olduğu önemli değildir (Java en iyi uygulamaları temel kuralı). Diğer yandan, flybywire postasına katılıyorum. İstihbaratımızı yöntem adını olabildiğince azaltmaya çalışmak için açıklamalıyız, ancak tanımlayıcılığını azaltmadan. Açıklayıcılık daha önemlidir :)


0

Bir ad, çok uzunsa:

  • Okumak 1 saniyeden uzun sürüyor
  • JVM'niz için ayırdığınızdan daha fazla RAM alır
  • Saçma sapan bir şey var mı
  • Daha kısa bir isim mükemmel mantıklıysa
  • IDE'nizde dolanıyorsa

Dürüst olmak gerekirse, adın amacını yalnızca onu bir genel API yöntemi olarak kullanacak veya ayrılırken kodu korumak zorunda olan Geliştiricilere iletmesi gerekir. Sadece KISS'i hatırla (basit aptal tut)

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.