2013-10-30 7 views
6
| * | 
| * | 
| * | 
| * | 
| * | 
| * | 
| * | 
| * | 
| * | 
| * | 
| * | 
| * | 
|* | 

Muszę wydrukować coś w rodzaju powyższego wykresu ASCII, aby rozwiązać problem Zagłady Gamblera. Gdzie bramka & bramka jest przyjmowana jako args. W lewo najbardziej | reprezentuje 0 dolarów, prawo najbardziej | reprezentuje cel, a * oznacza gotówkę w kasie. Mój program jest poniżej:Zrujnowanie Gambler ASCII w Javie

public class RuinPath { 

    public static void main(String[] args) { 
     // TODO - Your solution 

    int stake = Integer.parseInt(args[0]); // gambler's stating bankroll 
    int goal = Integer.parseInt(args[1]); // gambler's desired bankroll 

    { 
     int i = 0; 
     if (i == 0) { 
     System.out.print("|"); 
     i++; 
     while (i < stake) { 
      System.out.print(" "); 
      i++; 

      if (i == stake) { 
      System.out.print("*"); 
      i++; 

      while (i > stake && i < goal) { 
       System.out.print(" "); 
       i++; 

       if (i == goal) { 
       System.out.print("|"); 
       i = 0; 
       System.out.println(); 

       { 

        if (Math.random() < 0.5) { 

        stake++;  // win $1 
        } else { 
        stake--; // lose $1 

        } 

        if (stake == 1 || stake == goal - 1); 
        break; 

       } 
       } 
      } 
      } 
     } 
     } 
    } 
    } 
} 

co drukuje ten program mimo to:

| * | 
    *  | 
    * | 
     * | 
     * | 
     * | 
     * | 
     * | 
     * | 
     * | 
     * | 
     * | 
     * | 
     * | 
     * 

Dlaczego mój program nie pętli tak, że mogę dostać w lewo najbardziej | wydawać się reprezentować 0 dolarów przez całą drogę? Mam to, więc i = 0; na końcu pętli, aby po powrocie na pętlę powrócić do pętli, aż stawka będzie wynosić 1 lub mniej niż cel. Zamiast tego ponownie pętli od środka programu.

+2

Byłoby ciężko doświadczony programista nie popełnić błędu takiego, ze względu na swój przypadkowy wcięcia. –

+2

http://prettyprinter.de –

Odpowiedz

1

Oto wybuchł rozwiązanie, które może być łatwiejsze do rozumu o:

import java.io.PrintStream; 

public class SO { 
    private static int gambleWithCaution(int stake) { 
    if (Math.random() < 0.5) { 
     return stake+1; // win $1 
    } else { 
     return stake-1; // lose $1 
    } 
    } 

    private static void renderStanding(int stake, int goal) { 
    System.out.print('|'); 
    for(int dollar = 1; dollar< goal; dollar++) { 
     if(dollar == stake) { 
     System.out.print('*'); 
     } else { 
     System.out.print(' '); 
     } 
    } 
    System.out.println('|'); 
    } 

    public static void main(String ... args) { 
    int stake = Integer.parseInt(args[0]); // gambler's stating bankroll 
    int goal = Integer.parseInt(args[1]); // gambler's desired bankroll 

    while(stake > 0 && stake < goal) { 
     renderStanding(stake, goal); 
     stake = gambleWithCaution(stake); 
    } 
    System.out.println((stake > goal) ? "You Won!" : "You Lost"); 
    } 
} 

z wartościami 3 i 5 masz ten wynik:

| * | 
| * | 
|* | 
| * | 
| * | 
| *| 
| * | 
| *| 
You Won! 

Teraz, to jest oddzielona z was może się z tym bawić, np. tworząc funkcję hazardową w następujący sposób:

private static int gambleWithReclessAbandon(int stake, int goal, double abandon) { 
    int onTheLine = (int)(Math.random() * (int)(stake * abandon)); 
    if(stake < (0.5)*goal) { 
    //If you are at less than 50% of your goal then just put it all on the line 
    //and let it ride :) 
    onTheLine = stake; 
    } 
    if (Math.random() < 0.5) { 
    return stake+onTheLine; // win $ 
    } else { 
    return stake-onTheLine; // lose $ 
    } 
} 

który może być wywołany tak:

//Gamble up to 80% of your current stake 
stake = gambleWithReclessAbandon(stake, goal, 0.80); 

Z tych samych dwóch wartości jest to, co widziałem na moim pierwszym przejściu (byłem taaak blisko :)):

| * | 
| * | 
| *| 
| * | 
| *| 
You Lost 
+2

Doskonałe podejście. Zakładam, że jest to praca domowa, więc muszę powiedzieć, że jedną z najważniejszych rzeczy do nauczenia się jest to, jak zepsuć problem na mniejsze zestawy, które łatwiej można wizualizować i kodować mentalnie. – sb8244

+0

Czy istnieje sposób, aby ten sam program mógł być napisany w prostszy sposób? Podobnie jak bez printStream, ponieważ jestem na początku kursu Java i nie mogę do końca zrozumieć kodu, chociaż widzę, że działa i mój test mija. Próbuję się tego nauczyć, nie szukając właściwej odpowiedzi. Dziękuję Ci! – user2874403

+0

Wziąłem System.out PrintStream z funkcji 'renderStanding()'. Mam tendencję do pisania funkcji wyjściowych w ten sposób, ponieważ daje mi to elastyczność w drodze do wyjścia do baz danych lub JFrames, czy cokolwiek innego :) –

1

Twoja logika jest trochę zbyt skomplikowane. Ponadto twoje wcięcie sprawi, że jakiekolwiek debugowanie będzie niezwykle trudne.

Wystarczy wziąć jeden krok na raz:

public class RuinPath { 
    public static void main(String[] args) { 
     int stake = Integer.parseInt(args[0]); // Starting bankroll 
     int goal = Integer.parseInt(args[1]); // Desired bankroll 

     while (stake > 0 && stake < goal) { 
      System.out.print("|"); 

      // Print out the spaces. Using a for loop and 
      // printing a "*" if the counter variable 
      // is equal to stake is good way to do it. 

      // Flip a coin and increment/decrement the stake 

      System.out.print("|\n"); 
     } 
    } 
}