Javaの委任パターンが説明されている例を見ました。Objective-Cの柔軟性に欠けていると感じているため、あまり役に立ちませんでした(無知を許してください)。Objective-Cでできるようにデリゲートオブジェクトを動的に設定する方法はありますか? それが委任の要点ではないでしょうか。Java に関する私の知識は非常に予備的なものなので、少し詳しく説明してください。
2 に答える
Java で委任パターンを実装する方法はたくさんあると思いますが、組み込みのように感じられる方法はおそらくないでしょう。
ウィキペディアの例を見てください。基本的なオプションは、 interface を手動で実装してから、実行時に必要なだけ変更できる具体的なインスタンスに呼び出しを転送することです。
持っているツールと使用できるツールに応じて、この転送をより自動化できます。1 つのアイデアは、AspectJ のようなアスペクト指向プログラミングを使用することです。
アスペクト コンパイラ (またはランタイム) があれば、アノテーションを利用して、言語の簡単な拡張を考え出すことができます。
class Person {
@Delegate Animal animal;
...
}
次に、 を見つけてクラスの (例: ) インターフェイス@Delegate
に転送メソッドを自動的に追加するアスペクトを作成する必要があります。Person
よりグルーヴィーな JVM 言語を使用できる場合、そのような言語には標準ライブラリにデリゲートがあるため、コードを 1 行も記述する必要はありません。
Groovy でどのように行われるかについては、こちらを参照してください。Person
(本質的には、私が思いついた構文例とまったく同じですが...組み込みです!)
これは、Java で関数型イディオムを偽造する方法です。はい、それは恐ろしいです。洗練された関数型イディオムが必要な場合は、赤毛の義理の子供のように関数を扱わない言語を使用してください。コンパイル時の安全性をさらに高めたい場合は、もちろん、より具体的なインターフェイス定義を使用して、プログラミング エラーから IndexOutOfBounds と ClassCastException を取得しないようにすることができます。
public interface DelegatedFunction<T> {
T call(Object... args);
}
public class DoesSomeDelegatedTask {
private List<DelegatedFunction<String>> delegatedFunctions = new ArrayList<>(1);
public void addFunction(DelegatedFunction<String> function) {
delegatedFunctions.add(function);
}
public void execute() {
for (DelegatedFunction<String> function: delegatedFunctions) {
System.out.println(function(something, someotherthing, whatever));
}
}
}
public class Main {
public static void main(String[] args) throws Exception {
DoesSomeDelegateTask doer = new DoesSomeDelegatedTask();
doer.addFunction(new DelegatedFunction<String> () {
@Override
public String call(Object... args) {
return ((SomeThings) args[0]).whatever((SomeOtherThing) args[1]//you get the idea
}
}
doer.execute();
}
}