2012-02-23 9 views
0

特定の種類の情報を検索するために、(RegExパターンを使用して)解析する必要がある文字列のコレクションがあります。情報の「種類」には、電子メールアドレス、IPアドレス、FQDNなどがあります。ソース文字列には、単一の値(1つの電子メールアドレス)、同じタイプの複数の値(たとえば2つのIPアドレス)、値の混合(電子メールアドレスとIPアドレス)、または何も指定できません。これは工場パターンとして保証されていますか?

見つかったパターンを表すために、タイプ(電子メール、IPなど)とその値のプロパティを持つ1つのクラスがあります。どのようなメソッドでも、解析では、そのクラスのリストが返されます。ここで、カウントは0、1、またはそれ以上になります。

私の質問は、このタイプのシナリオはファクトリパターンにとって理にかなっていますか?コンストラクタは単一のクラスインスタンスを返すので、文字列がパラメータとして渡されるコンストラクタは使用できません。

私は抽象的なファクトリ・アプローチについて書いていますが、私の読書を形成しています。ファクトリは異なるクラスを返すように設計されています。

私は、WebRequestクラスの静的なCreate()メソッドがFactoryパターンであると述べている別のStackOverflow質問を読んでいます。だから私の考えは、ソース文字列を渡すことでそれを行うことができますか?

更新:この応答(http://stackoverflow.com/a/4828511/240372)に基づいて、「同じインターフェイスの別個の実装」がある場合は、工場パターンを使用する必要があります。だから私の要件はその基準を満たしていない。だから... ...私は最善のアプローチ...

編集に失われた小さな午前:私は、電子メールアドレスとIPアドレスの私の使用例は、人々は私が唯一の「アドレス」を扱っています思考との混同を追加するかもしれないと思います。そうではありません。説明のために疑似コードを追加してみましょう。

Class TypeClass 
    Property Name As String 
    Property Pattern As String 
End Class 

Class FoundValue 
    Property TypeName As String 
    Property Value As String 
End Class 

Dim possibleTypes as List(Of TypeClass) 
possibleTypes.Add(New TypeClass() With {.Name = "Email", .Pattern = "some_regex_pattern" } 
possibleTypes.Add(New TypeClass() With {.Name = "IPAddress", .Pattern = "some_regex_pattern" } 
possibleTypes.Add(New TypeClass() With {.Name = "Date", .Pattern = "some_regex_pattern" } 
possibleTypes.Add(New TypeClass() With {.Name = "Integer", .Pattern = "some_regex_pattern" } 

Dim sourceStrings as List(Of String) 
sourceStrings.Add("hello") 
sourceStrings.Add("1.2.3.4") 
sourceStrings.Add("[email protected]; [email protected]") 
sourceStrings.Add("C:\Windows\notepad.exe 24 [email protected]") 

For Each source in sourceStrings 
    For Each type in possibleTypes 
     ' compare type.pattern to source and return list of list of FoundTypes 
     ' 
     ' for example, the last source string would return: 
     ' list containing 
     '  New FoundValue() With { .TypeName = "Integer", .Value = "24" } 
     '  New FoundValue() With { .TypeName = "Email", .Value = "[email protected]" } 
     ' 
     ' whereas the second source would return 
     ' list containing 
     '  New FoundValue() With { .TypeName = "IPAddress", .Value = "1.2.3.4" } 

ありがとうございます。

+0

あなたの質問は「私のアドレス実装のセットを使用して文字列を評価するにはどうすればよいですか?」です。私はあなたがEmailAddress、IPAddressなどを持つことができると思います*共通のものがある場合* IAddressインターフェイス*を実装します。文字列を評価する場所では、IAddressのリストを返すことができます。しかし、それはファクトリーパターンではありません – kaj

答えて

0

私はあなたのテキストから、「物事」の種類を読み取るための共通のインターフェースを作りたいようですが、私に聞こえる

SO-と思ういけません。私は、以下のインターフェースを実装するそれぞれの異なるタイプの具体的なクラスを作成します。

public interface IThingReader 
{ 
    IEnumerable<Thing> ReadThing(string content); 
} 

このアプローチでは、単一の場所に読み取り/解析/建設にアドレスの特定のタイプをカプセル化することができます。あなたのケースでは、読者の集まりを収容するクラスを構築し、すべての結果を結合することができます。例:

public class CompositeReader 
{ 
    IThingReader[] Readers; 

    public CompositeReader(IThingReader[] readers) 
    { 
     Readers = readers; 
    } 

    public List<Thing> ParseText(string text) 
    { 
     List<Thing> allThings = new List<Thing>(); 

      foreach(IThingReader reader in Readers) 
      { 
       IEnumerable<Thing> things = reader.ReadThing(text); 
       allThings.AddRange(things); 
      } 

     return allThings; 
    } 
} 

文字列に含まれているものの種類を特定し、適切な結果を返さなければならない場合は、もっと便利です。したがって、上記の例では、作成するThingクラス(共通インタフェース)の異なる実装を決定するためにファクトリを使用しています。

0

ここでは、「同じインターフェイスの別個の実装」がないため、ここでは工場パターンは必要ありません。あなたがリストとどこに住所を作成を作成します。

あなたのパーサーは、だから、2つの作成のポイントを持って、このスタイル

List<Address> result = new empty list; 

for each found address 
     Address oneAddress = new Address 
     result.put(oneAddress) 

でコードを持っているかもしれません。いずれの場合も、作成するタイプを知っているので、デザインは現在、工場を必要としません。

代わりにあなたが

Interface Address 
Class EmailAddress implements Address 
Class IpAddress implements Address 

を持っていた、あなたはよく正しいアドレスオブジェクトを作成するために、工場出荷時のパターを使用する場合があります。

関連する問題