112

ここでの私のコードは、がいくつかのMIMEmimeTypeタイプと等しいかどうかを検出し、等しい場合は、特定の変換を行います

public void convertToMp3(File src, File target,String mimeType){
    if(mimeType.equals("audio/mpeg")){
        ...
    }else if(mimeType.equals("audio/wav")){
        mp3ToWav();
    }else if(mimeType.equals("audio/ogg")){
        ...
    }else if(...){
    ... //More if and else here
}

他に多くのifステートメントがあるため、コードを短縮しました。多くのifおよびelseまたはelse ifステートメントを削除するのに適したデザインパターンは何ですか?

4

7 に答える 7

192

あなたはConverterインターフェースを持つことができます。次に、次のようにMimetypeごとにクラスを作成できます。

public interface Converter {

    public void convertToMp3();
    public void convertToOgg();

}

public class MpegConverter implements Converter {

    public void convertToMp3() {
        //Code here
    }

    public void convertToOgg() {
        //Code here
    }

}

コンバーターごとにこのようなクラスが必要になります。次に、次のようなマップを設定できます。

Map<String, Converter> mimeTypeMap = new HashMap<String, Converter>();

mimeTypeMap.put("audio/mpeg", new MpegConverter());

次に、convertToMp3メソッドは次のようになります。

Converter converter = mimeTypeMap.get(mimeType);
converter.convertToMp3();

このアプローチを使用すると、将来、さまざまなコンバーターを簡単に追加できます。

すべてテストされておらず、おそらくコンパイルされませんが、あなたはアイデアを得る

于 2013-01-03T10:17:11.310 に答える
23

JDK7より前のバージョンを使用する場合は、すべてのMIMEタイプの列挙型を追加できます。

  public static enum MimeTypes {
      MP3, WAV, OGG
  }

  public class Stuff {
      ...
      switch (MimeTypes.valueOf(mimeType)) {
          case MP3: handleMP3(); break;
          case WAV: handleWAV(); break;
          case OGG: handleOGG(); break;
      }
  }

また、文字列を列挙型に変換する方法については、スタックオーバーフローの質問Java-文字列を列挙型に変換するをご覧ください。

于 2013-01-03T10:28:27.840 に答える
15

ストラテジーデザインパターンとを使用しMapて、適切なストラテジーにディスパッチすることを検討してください。特定の変換に加えて追加の機能が必要な場合、またはコンバーターが大きくて複雑なコードであり、各コンバーターを独自のファイルmimeTypeに配置したい場合に特に便利です。.java

 interface Convertor {
    void convert(File src, File target);
 }

 private static void convertWav(File src, File target) {
    ...
 }

 ...

 private static final Map< String, Convertor > convertors = new ...;
 static {
    convertors.put("audio/wav", new Convertor {
       void convert(File src, File target) {
          convertWav(src, target);
       }
    });
    convertors.put("audio/ogg", new Convertor {
       void convert(File src, File target) {
          convertOgg(src, target);
       }
    });
    ...
 }

 public void convertToMp3(File src, File target, String mimeType){
     final Convertor convertor = convertors.get(mimeType);
     if (convertor == null ) {
        ...
     } else {
        convertor.convert(src, target);
     }
 }
于 2013-01-08T13:59:48.117 に答える
3

それぞれの場合に同じメソッドを実行する場合は、状態パターンを確認する必要があります

于 2013-01-03T10:14:49.313 に答える
2

を使用している場合は、次のように構成JDK 7できます。switch-case

参照:文字列をオンにできないのはなぜですか?

以前のバージョンでif-elseは、が唯一の選択肢です。

于 2013-01-03T10:14:20.120 に答える
2

それは間違いなく戦略デザインパターンです。しかし、あなたはあなたの一般的なデザインに大きな問題を抱えています。文字列を使用して型を識別するのは、プログラミングの習慣としては適切ではありません。簡単に編集でき、文法の間違いを犯して、午後中ずっとプログラミングの間違いを探すことができるからです。map<>の使用を避けることができます。

私は次のことを提案します:

  1. クラスFileを拡張します。新しいクラスは、新しい属性FileTypeと新しいメソッドconvertTo(FileType)をクラスFileに追加します。この属性はそのタイプを保持します:「audio」、「wav」...そして再びStringを使用せず、Enumを使用します。この場合、私はそれをFileTypeと呼びました。必要なだけファイルを拡張します:WavFile、AudioFile .. ..
  2. Strategydpを使用してコンバーターを作成します。
  3. Factory dpを使用して、コンバーターを初期化します。
  4. すべてのファイルは独自のタイプとターゲットタイプを知っているため(convertTo()メソッドを使用してターゲットタイプを指定します)、ファクトリを呼び出して正しいコンバーターを自動的に取得します!!!

この設計はスケーラブルであり、FileTypeとコンバーターを必要なだけ追加できます。あなたが投票する答えは誤解を招くです!!!! コーディングとハッキングには大きな違いがあります。

于 2013-01-09T22:43:53.490 に答える
0

Java 7を使用していない場合は、を作成し、enumその値をswitch大文字小文字で使用できます。次に、列挙値を渡すだけで済みます(ファイルではなく、なぜそうしているのかはわかりません)。それもきれいに見えるでしょう。

これらはあなたがやりたいことを助けるはずです:

 [Java Enum Examples][1] - 
 [Java Switch Case examples][2]
于 2013-01-03T10:28:44.673 に答える