2011-03-18 5 views
7

Clojureについてのセッションを実行したいと思います。 Clojureで関数型プログラミングを使って優雅に解決できる問題をお勧めしますか?このトピックを扱うリソースを指摘できますか?Clojureの優れたショーケースは何ですか?

+0

どのようなセッションですか? 1時間、1日、1週間で説明できる問題と解決策をお探しですか?多くの可能性があります。 –

+0

私たちは、新技術を展示するための全社的な定期ショーケースイベントを開催しています。それは、セッションで2時間ハンドとして意図されています。 – spa

答えて

12

のClojureを使用するための引数の多くのカップルは、同時実行の取り扱いに関連すると思われるが、私はここでその問題には触れません。

私は、週にJavaを使用して週を処理しなければならないいくつかの問題と、Clojureでどのように解決するか、解決する方法をリストアップします。 Javaでは

不変

不変性を達成することは非常に非常に困難です。厳密なコーディングの慣行に加えて、フレームワークとライブラリを非常に慎重に選択する必要があります。副作用として、きれいで使いやすいAPIを作るためにたくさんのコードを書いたり、クライアントに対処させたりするだけです。 Clojureので

final Person person = personDao.getById(id); 
// I would like to "change" the person's email, but no setters... :(

あなたはので、あなたのすべてのオブジェクトは、デフォルトでは不変であり、これによるClojureのにこれらの構造を操作する強力な機能を提供しています不変のデータ構造に基づいてデータをモデル化します。 Javaでは

(let [person   (get-by-id person-dao id) 
     person-with-email (assoc person :email email)] 
    ; Use person-with-email... 

変換

あなたはフィールドidnameemailsocialSecurityNumberなどとドメインクラスPersonを持っています。データベース内のすべての人物の名前と電子メールを取得するためのWebサービスを作成しています。ドメインを公開したくないので、nameemailを含むクラスPersonDtoを作成してください。これは簡単だったので、PersonからPersonDtoにデータをマッピングする関数が必要になりました。おそらくこれは次のようなものです:

public class PersonPopulator { 
    public PersonDto toPersonDto(Person person) { 
     return new PersonDto(person.getName(), person.getEmail()); 
    } 

    public List<PersonDto> toPersonDtos(List<Person> persons) { 
     List<PersonDto> personDtos = new ArrayList<PersonDto>(); 
     for (Person person : persons) { 
      personDtos.add(toPersonDto(person)); 
     } 
     return personDtos; 
    } 
} 

これはあまり良くありませんでしたが、もっとデータをDTOに入れたいのですが?まあ、toPersonDtoのコンストラクタコードは少し心配する必要はありません。上記のようなユースケースが2つあり、電子メールだけを送信したい場合はどうなりますか?さて、私たちはnameをnullにしたり(悪い考え方)、新しいDTOを作成するかもしれません。恐らくPersonWithEmailDtoです。そこで新しいクラスを作成し、データを取り込むためのいくつかの新しいメソッドを作成します...これはどこにあるのでしょうか?にアドホックデータを追加することも

(map #(person-with-fields % :name :email) persons) 

:人物のリストを操作するため

(defn person-with-fields [person & fields] 
    (reduce #(assoc %1 %2 (get person %2)) {} fields)) 

(person-with-fields {:id 1 
        :name "John Doe" 
        :email "[email protected]" 
        :ssn "1234567890"} :name :email) 
; -> {:email "[email protected]", :name "John Doe"} 

そして:

Clojureの、不変のデータ構造と動的型付け言語では、私はこれを行うことができます人は簡単でしょう:

(assoc person :tweets tweets) 

これは何も破れません。 Javaでは、オブジェクトが不変の場合はおそらくセッターがないので、1つのフィールド(new Person(oldPerson.getName(), oldPerson.getEmail(), tweets)を変更するために多くの定型文を書くか、まったく新しいクラスを作成する必要があります。変更可能なオブジェクトは素晴らしいAPI(oldPerson.setTweets(tweets))を提供しますが、テストして理解することは難しいです。

をテスト

Javaコードの多くは、それが必要でない場合でも、いくつかの状態に基づいています。これは、テスト可能性を念頭に置いてコードを作成していない場合、通常は追加の定型文を意味し、この状態を模擬することができることを意味します。一方、モックのないテストは、通常遅く、データベースへのアクセスや時間、またはあなたが必ず失敗することになります。

Clojureをコーディングしている間、私は実際にそれほど多くのことを述べる必要はないことに気付きました。私が「外部」から何かを取得しているのは、データベースやWebサービスなのです。

概要

私のコードは、私はいくつかのデータを取得する一端から配管で、このデータは、それがの終わりに達するまで、いくつかの他のデータとを形質転換または接合、フィルタリングを介してパイプに変更されますパイプ。パイプの内部では、実際にデータを変更する必要はありませんが、強力な関数と不変のデータ構造が有用な場合が多く、Clojureがこのようなコードで不思議に思うのはこのためです。

+0

うわー、素晴らしい例。 – defhlt

+0

私は要約が好きだった。それはClojureと3ヶ月間働いている間に私がどのように感じたかです。 –

1

私は同じ問題を抱えており、Clojureの 'Mona Lisa'問題を解決することに決めました。結果はthis presentationでした。基本的に、Clojureは「コードとしてのデータ」が優雅なソリューションを提供する問題を解決するために非常に涼しいことを示しました。たとえば遺伝的アルゴリズムの場合。

関連する問題