セむロンたたはコトリンに完党に切り替える必芁がある理由パヌト1

最近、Kotlinの人気が高たっおいたす。 しかし、より゚キゟチックな蚀語を遞択し、それらに同じ匕数を適甚しようずするずどうなりたすか 蚘事はこれに基づいお曞かれおおり、Kotlinのすべおの議論を事実䞊繰り返しおいたす。 䞻なタスクJavaに関しお、Ceylonが実質的にKotlinず同じであるこずを瀺すこず。 しかし、これに加えお、セむロンには次の蚘事で説明する䜕か他のものがありたす。


Ceylonず呌ばれる新しいプログラミング蚀語に぀いお話し、次のプロゞェクトで䜿甚する理由を説明したいず思いたす。 私はJavaを䜿甚しお10幎以䞊、Java 1.4で始たりJava 8で終わる10幎以䞊、Javaが奜きでした。 それからScalaは私に倧きな印象を䞎えたした。その結果、蚀語ずしおのJavaが少しだけ奜きになり始めたした。 しかし、運呜はセむロン蚀語ず䞀緒に私をもたらしたした、そしお、この䞀幎半で、我々はどこでもセむロンを曞いおいたした。 実際の商業プロゞェクトでは、真実は内郚にありたす。 そしお、珟時点では、Javaを遞択したほうがよい状況を想像しおいたせん。Javaを新しいプロゞェクトを開始する䟡倀がある蚀語ずは考えおいたせん。


CeylonはRed Hatで開発され、蚀語の䜜成者はHibernateなどのフレヌムワヌクで知られるGavin Kingです。 Javaの欠点をよく理解しおいる人々によっお䜜成されたした。䞻な目暙は、玔粋に適甚された問題を解決し、コヌドの読みやすさを可胜な限り容易にし、曖昧さや萜ずし穎を避けるこずでした。 蚱容可胜なコンパむル時間にも倚くの泚意が払われたした。 珟圚、蚀語バヌゞョンは1.3.2であり、バヌゞョン1.2.0がリリヌスされたずきに蚀語を盎接知りたした。


CeylonはJavaScriptでコンパむルしたすが、䞻な環境であるJVMに集䞭したす。


そのため、Ceylonに完党に切り替える必芁があるいく぀かの理由順序は、察応するKotlin蚘事の同じ名前のアむテムず同じです


0Javaの互換性


Kotlinのように、Scalaのように、Ceylonは100Java互換です。 文字通り、叀いJavaプロゞェクトで䜜業を続けるこずができたすが、すでにCeylonを䜿甚しおいたす。 すべおのJavaフレヌムワヌクも利甚できたす。どのフレヌムワヌクを䜜成する堎合でも、Ceylonは頑固なJavaの愛奜家に簡単に受け入れられたす。 Java Ceylonから問題なくコヌドを呌び出すこずができ、Javaコヌドも問題なく呌び出されたす。


1䜿い慣れた構文


Ceylon蚀語の䞻な機胜の1぀は、既存の開発者にずっお最も読みやすい構文です。 既存のJava開発者を取り䞊げる堎合、Ceylon構文を理解しおいれば、圌はわずかな問題を抱えるこずはありたせん。 ScalaやKotlinのような蚀語でさえ、Javaにはあたり䌌おいたせん。 以䞋は、Kotlinの䟋に䌌た、かなりの数の蚀語構成を瀺すコヌドです。


class Foo(String a) { String b= "b"; // unmodifiable variable Integer i = 0; // variable means modifiable void hello() { value str = "Hello"; print("``str`` World"); } Integer sum(Integer x, Integer y) { return x + y; } Float maxOf(Float a, Float b) => if (a > b) then a else b } 

したがっお、Ceylonで簡単にJavaスタむルで曞き続けるこずができたす。


2文字列補間


これは、蚀語に組み蟌たれたJavaのString.formatのよりスマヌトで読みやすいバヌゞョンのようなものです。


 value x = 4; value y = 7; print("sum of ``x`` and ``y`` is ``x + y``") ; // sum of 4 and 7 is 11 

ここの構文は、Kotlinの構文よりも快適です。Javaず比范したくはありたせん。


3型掚論


読みやすさが向䞊するず思われる堎合、Ceylonはタむプを出力したす。


 value a = "abc"; // type inferred to String value b = 4; // type inferred to Integer Float c = 0.7; // type declared explicitly List<String> d = ArrayList<String>(); // type declared explicitly 

4スマヌトキャスト


Ceylonコンパむラヌはロゞックを監芖し、可胜な堎合は自動的に型倉換を実行したす。぀たり、明瀺的なキャスト埌のinstanceofチェックは䞍芁になりたす。


 if (is String obj) { print(obj.uppercased) // obj is now known to be a String } 

5盎芳的に等しい


==挔算子が構造的な等䟡性をチェックするようになったため、明瀺的にequalsを呌び出すこずはできなくなりたした。


 value john1 = Person("John"); //we override equals in Person value john2 = Person("John"); print(john1 == john2); // true (structural equality) print(john1 === john2); // false (referential equality) 

6デフォルト匕数


匕数が異なる耇数の同䞀のメ゜ッドを定矩する必芁がなくなりたした。


 void build(String title, Integer width = 800, Integer height = 600) { return Frame(title, width, height); } 

7名前付き匕数


デフォルトの匕数ず組み合わせお、名前付き匕数を䜿甚するず、ビルダヌを䜿甚する必芁がなくなりたす。


 build("PacMan", 400, 300) // equivalent build {title = "PacMan"; width = 400; height = 300;} // equivalent build {title = "PacMan"; height = 300;} // equivalent with default width 

8匏スむッチ


分岐挔算子は、はるかに読みやすく柔軟なswitchステヌトメントに眮き換えられたした。


 switch (obj) case(1) { print("x is 1"); } case(2) { print("x is 2"); } case(3 | 4) { print("x is 3 or 4"); } case(is String) { print ("x is String"); } case([Integer a, Float b, String c]) {print ("x is tuple with Integer ``a``, Float ``b`` and String ``c``");} else { print("x is out of range");} 

スむッチは匏ずしお機胜し、スむッチの結果を倉数に割り圓おるこずもできたす。


 Boolean|IllegalStateException res = switch(obj) case(null) false case(is String) true else IllegalStateException(); 

これは本栌的なパタヌンマッチングではありたせんが、ほずんどの堎合、珟圚の機胜で十分です。


Kotlinずは異なり、Ceylonでは、スむッチのすべおの条件が互いに玠である必芁がありたす。぀たり、オヌバヌラップしないこずが必芁です。 範囲の䞀臎が必芁な堎合、たたは条件が亀差する堎合は、通垞のifを䜿甚する必芁がありたす。


9プロパティ


カスタムセットを远加しお、パブリックフィヌルドにビヘむビアを取埗できたす。぀たり、クレむゞヌなゲッタヌずセッタヌでコヌドの入力を停止できたす。


 class Frame() { variable Integer width = 800; variable Integer height = 600; Integer pixels => width * height; } 

10デヌタクラス


残念ながら、この機胜はただ利甚できたせん。 toString、equals、hashCode、copyを自動的にオヌバヌラむドする䞍倉のクラスが必芁ですが、Javaずは異なり、100行のコヌドを占有したせんでした。


しかし、これがただ蚀語にないずいう事実は、それが䞍可胜であるこずを意味したせん。 蚀語自䜓を䜿甚するラむブラリを介しお、目的の機胜を実装する方法の䟋を瀺したす。


 class Person(shared String name, shared String email, shared Integer age) extends DataObject() {} value john = Person("John", "john@gmail.com", 112); value johnAfterBirhstday = john.copy<Person>({`Person.age`->113;}); assertEquals(john, john.copy<Person>()); assertEquals(john.hash, john.copy<Person>().hash); 

぀たり、ラむブラリレベルでは、toStringを再定矩し、クラスを䞍倉のたたにしおおくこずが可胜で、個々の属性を倉曎したクロヌンを䜜成する機䌚がありたした。 残念ながら、これはサポヌトが蚀語で行われた堎合ほど速く動䜜したせん。 たた、コンパむル時に型チェックはありたせん=幎霢で再定矩しおクロヌンを䜜成し、倀ずしお文字列を指定するず、実行時に゚ラヌが発生したす。 そのような機胜がただないずいう事実は確かに悪いです。 しかし、必芁に応じおラむブラリレベルで独立しお必芁な機胜を蚘述できるずいう事実は非垞に優れおいたす。


11オペレヌタヌのオヌバヌロヌド


読みやすくするためにオヌバヌロヌドできる事前定矩された䞀連の挔算子


 class Vec(shared Float x, shared Float y) satisfies Summable<Vec> { shared actual Vec plus(Vec v) => Vec(x + vx, y + vy); } value v = Vec(2.0, 3.0) + Vec(4.0, 1.0); 

12宣蚀の砎壊


䞀郚のオブゞェクトは砎棄できたす。これは、たずえば、マップの反埩凊理に圹立ちたす。


 for ([key -> [val1, val2, val3]] in map) { print("Key: ``key``"); print("Value: ``val1``, ``val2``, ``val3``"); } 

13範囲


読みやすさを改善するには


 for (i in 1..100) { ... } for (i in 0 : 100) { ... } for (i in (2..10).by(2)) { ... } for (i in 10..2) { ... } if (x in 1..10) { ... } 

察照的に、KotlinはキヌワヌドdownToなしで実行したした。


14拡匵機胜


圌らはそこにいたせん。 初期の蚀語仕様では、このような可胜性が考慮されおいたようです。 ただし、原則ずしお、拡匵機胜の代わりにトップレベルの機胜が機胜したす。 たずえば、sayHelloメ゜ッドをStringクラスに远加する堎合、「world」.sayHelloはsayHello「world」よりも芋栄えがよくありたせん。 将来的には衚瀺される可胜性がありたす。


原則ずしお、クラスで䜿甚可胜な察応する関数はIDE自䜓で芋぀けるこずができたすが、動䜜するこずもありたす。


15Nullセキュリティ


Javaはほが静的に型付けされた蚀語ず呌ばれるべきです。 その内郚では、String型の倉数はStringを参照するこずが保蚌されおいたせん-nullを参照する堎合がありたす。 私たちは慣れおいたすが、これは静的型付けチェックのセキュリティを䜎䞋させ、その結果、Java開発者はNPEに察する絶え間ない恐怖に耐えざるを埗たせん。


Ceylonでは、null倀を蚱可するタむプず蚱可しないタむプを分離するこずで、この問題を解決したした。 デフォルトでは、型はnullを蚱可したせんが、远加するこずで型を蚱可するように倉換できたすか


 variable String a = "abc"; a = null; // compile error variable String? b = "xyz"; b = null; // no problem 

ナニオン型文字列の機胜のためですか それはString | Nullの単なる構文糖です。 したがっお、次のように蚘述できたす。


 variable String|Null  = "xyz";  = null; // no problem 

Ceylonを䜿甚するず、null蚱容型を呌び出すずきにNPEず栌闘できたす。


 value x = b.length // compile error: b might be null 

倧きく芋えるかもしれたせんが、いく぀かの機胜のおかげで非垞に䟿利です。 nullを蚱可する型をnullを蚱可しない型に倉換する堎合でも、スマヌトな型倉換がありたす。


 if (!exists b) { return; } value x = b.length // no problem 

安党な呌び出しを䜿甚するこずもできたすか。、NPEをスロヌする代わりにnullを返したす。


 value x = b?.length; // type of x is nullable Int 

セキュアコヌルをチェヌンしお、他の蚀語で蚘述されるこずがあるネストされたnullでないifチェックを回避できたす。 デフォルトでヌル倀が必芁ない堎合は、elvis else挔算子を䜿甚したす


 value name = ship?.captain?.name else "unknown"; 

これらのすべおがあなたに合わず、あなたが絶察にNPEを必芁ずするなら、そう明瀺的に蚀っおください


 value x = b?.length else NullPointerException() // same as below assert(!NullPointerException x); 

16改善されたラムダ


これは優れたラムダシステムです。いく぀かの賢明な゜リュヌションのおかげで、読みやすさず簡朔さの完璧なバランスが保たれおいたす。 構文は簡単です


 value sum = (Integer x, Integer y) => x + y; // type: Integer(Integer, Integer) value res = sum(4,7) // res == 11 

したがっお、構文は次のようになりたす。


 numbers.filter( (x) => x.isPrime() ); numbers.filter(isPrime) 

これにより、簡朔な機胜コヌドを䜜成できたす。


  persons .filter ( (it) => it.age >= 18) .sort(byIncreasing(Person.name)) .map ( Person.email ) .each ( print ); 

ラムダシステムず蚀語の構文機胜により、CeylonはDSLを䜜成するための優れたツヌルになりたす。 Ceylon構文のAnkoのようなDSLの䟋


  VerticalLayout { padding = dip(30); { editText { hint = "Name"; textSize = 24.0; }, editText { hint = "Password"; textSize = 24.0; }, button { "Login"; textSize = 45.0; } } }; 

17IDEサポヌト


ちなみに圌女はずおもいいです。 Eclipseプラグむンがあり、IDEAプラグむンがありたす。 はい、機胜ずバグの点では、すべおがScalaやKotlinよりもやや悪いです。 しかし、原則ずしお、IDEの問題は実際には開発速床に圱響しないため、非垞に快適に䜜業できたす。


合蚈するず、Kotlinの匷みを掻甚するず、CeylonはDataObject機胜の欠劂によりKotlinに劣りたすラむブラリを䜿甚しお個別に゚ミュレヌトできたす。 それ以倖の堎合、それは以䞋の機胜を提䟛したすが、より読みやすい構文を備えおいたす。


たあ、Kotlinず同様に、CeylonはAndroid甚に䜜成できたす。


䞊蚘を読んだ埌、印象が生じるかもしれたせん-なぜこれが必芁なのですか 同じこずがKotlinにもあり、ほが1分の1です。


そしお、セむロンにはコトリンにもスカラにもないものがあるずいう事実ず、これらのこずのために、蚀語自䜓は他の蚀語よりもはるかに優れおいたす。 たずえば、ナニオン型、亀差型、列挙型、より匷力なゞェネリック、モゞュヌル性、矀れ、泚釈ずメタモデル、タプル、理解甚。 これにより、プログラミングぞのアプロヌチが倧きく倉わり、より信頌性が高く、理解しやすい、普遍的なコヌドを曞くこずができたす。 しかし、それに぀いおは次のパヌトで詳しく説明したす。




Source: https://habr.com/ru/post/J330412/


All Articles