• Najnowsze pytania
  • Bez odpowiedzi
  • Zadaj pytanie
  • Kategorie
  • Tagi
  • Zdobyte punkty
  • Ekipa ninja
  • IRC
  • FAQ
  • Regulamin
  • Książki warte uwagi

Czy da się uniknąć dużej liczby if-ów bądź switch-ów w wyborze poziomu?

VPS Starter Arubacloud
0 głosów
316 wizyt
pytanie zadane 18 kwietnia 2019 w C# przez Shimeo7 Obywatel (1,910 p.)
edycja 18 kwietnia 2019 przez Shimeo7

Witam wszystkich, chcę poprawić swój kod dotyczący wyboru poziomów, gdyż mam gigantycznego switcha, który składa się z 18 case-ów. Aktualnie działa to tak, że na każdy poziomie czyszczona jest lista w wrogami, dodaje wrogów do listy i broń jaka jest na danym poziomie, po zabiciu wszystkich wrogów, wywołuje funkcję klasy i przechodzę na case 2 i tak do case 18. Nie wiem, czy intuicja mi dobrze mówi, ale niezbyt dobrze taki switch wygląda. Dla poglądu sytuacji wrzucę kilka case-ów, żeby nie wrzucić 250 linii kodu

 case 8:
                    {
                        Enemies.Clear();
                        Enemies.Add(new Wizard(this, GetRandomLocation(random)));
                        if(CheckPlayerInventory("Bow"))
                            WeaponInRoom = new Quiver(this, GetRandomLocation(random));
                        break;
                    }
                case 9:
                    {
                        Enemies.Clear();
                        Enemies.Add(new Ghost(this, GetRandomLocation(random)));
                        Enemies.Add(new Ghoul(this, GetRandomLocation(random)));
                        if (CheckPlayerInventory("Bow"))
                            WeaponInRoom = new Shield(this, GetRandomLocation(random), 5);
                        else
                            WeaponInRoom = new Bow(this, GetRandomLocation(random));
                        break;
                    }
                case 10:
                    {
                        Enemies.Clear();
                        Enemies.Add(new Wizard(this, GetRandomLocation(random)));
                        Enemies.Add(new Bat(this, GetRandomLocation(random)));
                        if (CheckPlayerInventory("Red potion"))
                            WeaponInRoom = new BattleAxe(this, GetRandomLocation(random));
                        else
                            WeaponInRoom = new RedPotion(this, GetRandomLocation(random));
                        break;
                    }
                case 11:
                    {
                        Enemies.Clear();
                        Enemies.Add(new Wizard(this, GetRandomLocation(random)));
                        Enemies.Add(new Ghost(this, GetRandomLocation(random)));
                        if (CheckPlayerInventory("Battle axe"))
                            ;
                        else
                            WeaponInRoom = new BattleAxe(this, GetRandomLocation(random));
                        break;
                    }
                case 12:
                    {
                        Enemies.Clear();
                        Enemies.Add(new Bat(this, GetRandomLocation(random)));
                        Enemies.Add(new Ghost(this, GetRandomLocation(random)));
                        Enemies.Add(new Ghoul(this, GetRandomLocation(random)));
                        if (CheckPlayerInventory("Bow"))
                        {
                            if (CheckPlayerInventory("Quiver"))
                                ;
                            else
                                WeaponInRoom = new Quiver(this, GetRandomLocation(random));
                        }
                        break;
                    }

Chciałbym uprościć nieco logikę i zastanawiałem się nad funkcjami dla każdego poziomiu typu void, ale jestem zbyt cienki w uszach i jeszcze i być może czegoś nie widzę, dlatego chciałbym się spytać, co o tym sądzicie, czy może są jakieś lepsze rozwiązania na takie gigantyczne switche? A może utworzyć oddzielną klasę dla każdego z poziomu? Z góry dziękuję za odpowiedź.

 

komentarz 18 kwietnia 2019 przez NowyUrzydgownig Mądrala (5,090 p.)
Tak, możesz to rozbić, tworząc 2 metody - jedna do tworzenia przeciwników w zależności od poziomu, a druga do tworzenia ekwipunku w zależności od poziomu. Nie wiem, jak wygląda całość twojej gry, ale jeśli np. łuk jest na 2 poziomie, a potion na 3. To może warto stworzyć sobie enuma z ekwipunkiem na dany poziom.

2 odpowiedzi

0 głosów
odpowiedź 18 kwietnia 2019 przez DeBos123 Nałogowiec (44,950 p.)

Napewno możesz wyciągnąć Enemies.Clear() jeżeli i tak robisz to za każdym razem.

Co do przeciwników to ja bym zrobił tablicę vector'ów z x vector'ami, gdzie x to liczba poziomów.

Każdy vector przechowywałby wskaźniki na konstruktory i wtedy możnaby przed switch'a wyciągnąć coś takiego:

for(int i=0;i<EnemiesVectors[level].Length;i++){
    Enemies.Add(EnemiesVectors[level][i](this,GetRandomLocation(random)));
}

Co do broni to napewno dałoby się wymyśleć jakąś zależność.

0 głosów
odpowiedź 18 kwietnia 2019 przez Arkadiusz Fajdek Dyskutant (9,450 p.)
Hej! Oczywiście, że da się to wszystko ładnie posprzątać, i przede wszystkim uniknąć takiej złożonej struktury ifów. Jednak jest to temat złożony i trzeba by przeanalizować całą aplikację, być może problem zaczyna się gdzieś wcześniej ze złą organizacja. Nie jestem w stanie dać Ci konkretnego rozwiązania "zrób to i to", tak jak pisałem to może być bardzo złożone.

Jest taka naprawdę bardzo dobra książka "Clean Code", jest też Polskie wydanie Czysty Kod (polecam jednak angielską wersję), która właśnie mówi o tym jak refakturować kod aby pozbywać się takich struktur.

Podobne pytania

0 głosów
2 odpowiedzi 1,389 wizyt
0 głosów
1 odpowiedź 178 wizyt
–1 głos
1 odpowiedź 503 wizyt
pytanie zadane 25 czerwca 2020 w OpenGL, Unity przez jerk0 Użytkownik (540 p.)

92,957 zapytań

141,915 odpowiedzi

321,147 komentarzy

62,286 pasjonatów

Motyw:

Akcja Pajacyk

Pajacyk od wielu lat dożywia dzieci. Pomóż klikając w zielony brzuszek na stronie. Dziękujemy! ♡

Oto polecana książka warta uwagi.
Pełną listę książek znajdziesz tutaj.

Wprowadzenie do ITsec, tom 2

Można już zamawiać tom 2 książki "Wprowadzenie do bezpieczeństwa IT" - będzie to około 650 stron wiedzy o ITsec (17 rozdziałów, 14 autorów, kolorowy druk).

Planowana premiera: 30.09.2024, zaś planowana wysyłka nastąpi w drugim tygodniu października 2024.

Warto preorderować, tym bardziej, iż mamy dla Was kod: pasja (użyjcie go w koszyku), dzięki któremu uzyskamy dodatkowe 15% zniżki! Dziękujemy zaprzyjaźnionej ekipie Sekuraka za kod dla naszej Społeczności!

...