가위바위보 게임의 루프가 제대로 계속되지 않는 이유는 무엇입니까?

가위바위보 게임의 루프가 제대로 계속되지 않는 이유는 무엇입니까?

저는 bo3 가위바위보 게임을 만들고 있어요. 지금까지 나는 넥타이를 제외한 모든 조건에서 작동했습니다. 동점이 발생하면 I에서 1을 빼기만 하면 게임을 "다시 만들 수" 있다는 의미입니다. 그러나 작동하지 않는 것 같으며 그 이유를 이해하지 못합니다.

이것은 내 코드입니다.

#!/bin/bash

#rock beats scissors, scissors beats paper, paper beats rock, 
userwin=0
compwin=0

printf "Welcome to rock paper scissors. "

for i in {1..3}
do
    printf "Type 'r', 'p', or 's': "

    #get users selection
    read user

    #detect input and assign it to a num that will be used to check against computer.
    if [[ $user == [rR] || $user == "Rock" || $user == "rock" ]]
      then
        user="r"
    elif [[ $user == [sS] || $user == "scissors" || $user == "Scissors" ]]
      then
        user="s"
    elif [[ $user == [pP] || $user == "paper" || $user == "Paper" ]]
      then
        user="p"
    else
        printf "Not a valid submission, you entered: %s\n" "$user"
    fi

   #get random number between 1 and 9
   comp=$(shuf -i 1-9 -n 1)

   #detect what number it was and assign either r p s to it. 
   if ((1<=comp && comp<=3))
     then 
       comp="r"
       printf "Computer chooses rock\n"
   elif ((4<=comp && comp<=6))
     then
       comp="s"
       printf "Computer chooses scissors\n"
   elif ((6<=comp && comp<=9))
     then
       comp="p"
       printf "Computer chooses paper\n"
   else
       printf "not in range?"
   fi

   #find out who won
   if [[ $user == "$comp" ]]
     then
        i=$((i-1))
        printf "It's a tie, remake!\n"
   elif [[ $user == "r" && $comp == "p" ]]
     then
       printf "You lose!\n"
       compwin=$((compwin+1))
   elif [[ $user == "p" && $comp == "r" ]]
     then  
       printf "You win!\n"
       userwin=$((userwin+1))
   elif [[ $user == "s" && $comp == "r" ]]
     then  
       printf "You lose!\n"
       compwin=$((compwin+1))
   elif [[ $user == "r" && $comp == "s" ]]
     then  
       printf "You win!\n"
       userwin=$((userwin+1))
   elif [[ $user == "p" && $comp == "s" ]]
     then  
       printf "You lose!\n"
       compwin=$((compwin+1))
   elif [[ $user == "s" && $comp == "p" ]]
     then  
       printf "You win!\n"
   else
       printf "something is borked"
   fi

   if [[ $userwin == 2 ]]
     then
       printf "You win the bo3!\n"
       break
   elif [[ $compwin == 2 ]]
     then
       printf "You lose the bo3!\n"    
       break
   else
      reali=$((i+1))
      printf "\nGame %s start\n" "$reali"
   fi

done

실패한 게임의 예는 다음과 같습니다.

noah: [~/myFiles/scripts] ./rps.sh
Welcome to rock paper scissors. Type 'r', 'p', or 's': r
Computer chooses rock
It's a tie, remake!

Game 1 start
Type 'r', 'p', or 's': r
Computer chooses paper
You lose!

Game 3 start
Type 'r', 'p', or 's': r
Computer chooses scissors
You win!

Game 4 start
noah: [~/myFiles/scripts]

뭔가 내 I 정수가 엉망이 된 것 같지만 bash -x를 사용해도 왜 그런지 알 수 없습니다. 경험이 있는 사람이 이것을 확인할 수 있습니까?

답변1

for이와 같은 루프 내에서는 변수를 수정할 수 없습니다 bash. 아... 할 수는 있지만 반복에는 영향을 미치지 않습니다. C에서 익숙했던 계산 루프가 아닙니다.

최소한의 예:

#!/bin/bash
for i in {1..3}
do
    echo $i
    i=$((i-1))
    echo $i
done

분명히 다음과 같이 인쇄됩니다.

./b.sh 
1
0
2
1
3
2

Kusalananda가 제안한 대로 조건문이 포함된 표준 루프를 사용하는 것이 더 좋습니다.

#!/bin/bash
i=0
while ((i++ < 3)); do
    echo $i
    # your code here
    #i=$((i-1))
    #echo $i
done

또한 아래의 이전 제안을 유지하지만 위의 제안이 확실히 더 좋습니다.


실행 볼륨을 수정하려면 무한 루프를 사용하고 내부적으로 자체 변수를 처리하는 것이 좋습니다. 다음과 같은 것이 작업을 수행해야 합니다(예: 증분 2, 그렇지 않으면 절대 끝나지 않습니다):

#!/bin/bash
i=1
while true; do
    if [[ $i > "3" ]]; then
        break
    fi
    echo $i
    i=$((i-1))
    echo $i

    i=$((i+2))
done

관련 정보