2010-03-04 15 views
6

Od czasu do czasu robię tego typu rzeczy i zastanawiam się, czy to zapach projektu, czy też istnieje lepszy wzór projektu, którego mogę użyć.Iteracja nad listą typów

Istnieje proces z wieloma krokami, które są znane w czasie kompilacji, ale prawdopodobnie ulegną zmianie na drodze Uchwycę powszechność w abstrakcyjnej klasie Step, napiszę StepListera, który zwraca listę kroków, po jednym dla każdej pochodnej klasy Step, a następnie StepsRunner, który wywołuje StepLister, a następnie iteruje na liście i wykonuje każdy krok. Czasami jeden krok będzie zależał od wyniku z poprzedniego kroku, czasem nie.

Wszelkie sugestie?

Odpowiedz

2

Twoje podejście brzmi dla mnie rozsądnie (połączenie iteratorów/strategii).

Czasami jeden krok będzie zależał od wyniku z poprzedniego kroku, czasami nie.

Ten punkt może być jednak interesujący. Ponieważ nie wiem, co powinien zrobić każdy krok, mogę podać tylko ogólne pomysły.

Zależności między wszystkimi krokami można modelować za pomocą drzewa składni interpreter-like zamiast kolejnych kroków. W związku z tym twoje urządzenie StepRunner zostanie odrzucone na korzyść metod kontekstowych/interpretacyjnych.

Innym pomysłem może być użycie monads, które pozwalają kolejno kroki skleić, ale nie wiem jak to będzie łatwo zintegrować istniejące pojęcia obiektowego (od monady są zwykle używane w funkcjonalnego programowania).

Może nie trzeba (nad-) komplikować wcale;)

1

Nie jestem pewien, czy zrozumiał pytanie rację, ale skoro używasz czynności w kolejności, będzie Przypuszczam, że istnieje niektóre informacje kontekstowe są przechowywane, a zatem mówisz o wybraniu następnego kroku na podstawie wyniku bieżącego.

To jest właściwie to, o czym jest automat. Masz różne stany połączone ze sobą przejściami.

Dosyć łatwo jest poprosić o każdy krok, aby zwrócić pewną liczbę tag, może po prostu ciąg lub odpowiednio zdefiniowany typ.

Następnie należy zdefiniować automat określając kolejny krok dla każdego z możliwych wyjść bieżącego kroku.

Na przykład, faktycznie używam frameworka (w pracy), który przechwytuje te przejścia jako plik xml ... mimo że nie podoba mi się fakt, że nie dokonano niewielkiego sprawdzenia, czy przejścia są poprawnie zdefiniowane.

Zauważ, że w C++ można to sprawdzić w czasie kompilacji (myślę o użyciu Boost.Variant i kilku sztuczek programistycznych).