0

そのため、2 つのホテル カタログをマッピングするというタスクがあります。どちらも csv ファイルです。それぞれの責任に基づいて、次の 2 つのクラスを作成しました。 1. CatalogManager : カタログの I/O 操作を処理します。2. CatalogMapper : 2 つのカタログのマッピング タスクを処理します。

定義は次のとおりです。

public static class CatalogManager
{
   public static List<Hotel> GetHotels(string filePath) { }
   public static void SaveHotels (List<Hotel> hotels, string filePath) { }
   public static void SaveMappedHotels (List<MappedHotel> hotels, string filePath) { }
   public static List<string> GetHotelChains(string filePath) { }
}

public static class CatalogMapper
{
   public static List<MappedHotel> MapCatalogs (List<Hotel> masterCatalog, List<Hotel> targetCatalog) { }

   public static FetchAddressGeoCodes (Hotel.Address address)
   { // fetch address's geocode using Google Maps API }

   public static string GetRelevantHotelChain (string hotelName)
   {
      List<string> chains = CatalogManager.GetChains();
      // find and return the chain corresponding to hotelName. 
   }
}

典型的なマッピング操作は次のようになります。

List<Hotel> masterCatalog = CatalogManager.GetHotels(masterFilePath);
List<Hotel> targetCatalog = CatalogManager.GetHotels(targetFilePath);
List<MappedHotel> mappedHotels = CatalogMapper.MapHotels(masterCatalog, targetCatalog);
CatalogManager.SaveMappedHotels(mappedHotels, mappedCatalogFilePath);

コードが示すように、両方のクラスは静的です。それらが正しく機能していることはわかりましたが、OOP に関しては、この設計にはまだ何か問題があると感じています。両方のクラスが単純に静的であっても問題ありませんか? それらをインスタンス化する必要はありませんでした。また、この設計の他の欠陥は何ですか? 欠陥が存在することは確かです。それらの解決策は何ですか?

4

2 に答える 2

1

別の合理的なアプローチはCatalogManager、ファイル名で初期化された非静的クラスを作成することです。これにより、ファイルをメモリから部分的に使用し、必要に応じて読み取りまたは書き込みを行うことができます。

于 2011-10-10T11:24:24.183 に答える
1

無料機能を恐れないでください!

CatalogMapperをマップするのは疑わしいと思いますHotel.Address。適切に因数分解/カプセル化するには、

  • CatalogMapperホテル固有Addressではない で動作する必要があります。

  • または、Hotel.Addressどういうわけか特別な wrt GeoCodes である場合はHotel.AddressCatalogMapper.


コメントからの説明により、次のことを提案したいと思います。C# はわからないので、C++ で書きます。翻訳されることを願っています

struct Hotel {
    const Address & address () const;

    // I typedef EVERTYTHING :-)    
    typedef std :: list <std :: string> StringList;
    typedef std :: pair <Hotel, Hotel> Pair;
    typedef std :: list <Hotel> Container; // TODO implicit sharing?
    typedef std :: list <Pair> Mapping;

    // NB will be implemented in terms of std::istream operations below,
    // or whatever the C# equivalent is.
    // These could arguably live elsewhere.
    static Container load (const std :: string &);
    static Mapping load_mapping (const std :: string &);
    static void save (const std :: string &, const Container &);
    static void save_mapping (const std :: string &, const Mapping &);

    // No need for a "Manager" class for this.
    static StringList load_chain (const string & file_name);

private:
    static Hotel load (std :: istream &);
    void save (std :: ostream &) const;
};

// Global namespace, OK because of overloading. If there is some corresponding
// generic library function which merges pair-of-list into list-of-pair
// then we should be specialising/overloading that.
Hotel :: Mapping merge (const Hotel :: Container &, const Hotel :: Container &);

struct GeoCode {
   GeoCode (const Address &);
};

「マネージャー」と呼ばれるクラスを目にするたびに、それが他のオブジェクトへのアクセスを作成、所有、および制御するオブジェクトでない場合、それは私たちが名詞の王国にいるという警告アラームです. オブジェクトは自分自身を管理できます。ロジックが 1 つのクラスの範囲を超えている場合にのみ、そのロジック用に別のクラスを用意する必要があります。

于 2011-10-10T13:25:57.293 に答える