【问题标题】:What does IndexOutofRangeException mean?IndexOutofRangeException 是什么意思?
【发布时间】:2012-03-13 06:19:00
【问题描述】:

它说在我的数组中我已经检查了索引。我的程序是一个由 5 个玩家(5 个索引)玩的数字猜谜游戏。我使用数组来创建对象和播放器类。 我的程序在第二轮或第三轮比赛中崩溃了。我注意到在我的第二轮中,索引没有循环属性:循环在第一个循环中将索引计数为 1 到 5,然后在第二个循环中计数到 2 到 5,然后如果我什至进入第三轮循环,所有索引都被打乱了,这意味着我不能从 1 转到 5。

当每个玩家获得 3 次猜测时,使用这 3 次猜测并退出游戏。我已经获取了为播放器创建的对象数组,创建了一个比以前小的临时数组并引用它来实现当前数组。

我查看了代码中的引用并找到了尽可能多的代码,但我找不到导致 System.IndexOutOfRangeException 的错误。这是由我的猜谜游戏课引起的。

这是我的 GuessingGame 类:

using System;  // only this using statement is needed here.

namespace GuessingGame
{

class GuessingGame
{
  #region instance attributes
  private const int GUESSES_ALLOWED = 3;
  private const int NUMBER_OF_PLAYERS_TO_START = 5;
  private const int MIN_VALUE = 1;
  private const int MAX_VALUE = 15;
  private Player[] players;
  private Random randomSource;
  #endregion

  public GuessingGame()
  {
     Console.WriteLine("Starting Constructor of GuessingGame");
     players = new Player[NUMBER_OF_PLAYERS_TO_START];
     randomSource = new Random();

     string playerName = "";
     for (int index = 0; index < players.Length; index++)
     {
        Console.Write("What is the name for player #" 
              + (index +1) + "?\t");
        playerName = Console.ReadLine();
        players[index] = new Player(playerName, randomSource);
        Console.Write("\n");
     }
     Console.WriteLine("Ending GuessingGame Constructor");
  }

  public GuessingGame(string [] playerNames)
  {

     Console.WriteLine("Starting Constructor of GuessingGame");
     players = new Player[playerNames.Length];
     randomSource = new Random();
     for (int index = 0; index < playerNames.Length; index++)
     {
        players[index] = new Player(playerNames[index], randomSource);
     }
  }

  public void playGame()
  {
     int numberOfPlayersWhoHavePlayedThisRound = 0;
     int index = 0;

     bool[] playedThisRound = null;
     string playerGuessEntry = "";
     int playerGuessValue = -1;
     Player[] tempArray = new Player[players.Length - 1];
     bool roundOver = false; 

     Console.WriteLine(
           "Starting playGame - press any key to continue");
     //Console.Read()

     while (roundOver == false) // Is this the right condition?
     {

         playedThisRound = new bool[players.Length];


         while (playedThisRound[index] == false)
         {
             do
             {
                 Console.Write(players[index].getName()
                       + ", Enter a number between "
                       + MIN_VALUE.ToString()
                       + " and " + MAX_VALUE.ToString()
                       + " inclusive\t");
                 playerGuessEntry = Console.ReadLine();
                 Console.Write("\n");
             }
             while (!int.TryParse(playerGuessEntry,
                      out playerGuessValue)
                    || playerGuessValue < MIN_VALUE
                    || playerGuessValue > MAX_VALUE);
             if(playerGuessValue < MIN_VALUE || playerGuessValue > MAX_VALUE)
             {
                 Console.Write("Invalid guess- try again");
             }
             else
             {

                 Console.WriteLine("You entered "
                       + playerGuessValue.ToString());

                 players[index].makeAGuess(playerGuessValue);
                 playedThisRound[index] = true;
                if (index == players.Length)
                {
                    Console.WriteLine("End of Round");
                    index = 0; //edit?
                    numberOfPlayersWhoHavePlayedThisRound = 0;
                }

             }
             if (players[index].getGuessesUsed() == 3)
             {//creating a temp array
                 Console.WriteLine("Guesses MAXED");
                 tempArray = players[index].deletePlayerFromArray(players, index);
                 players = tempArray; // referencing
                 bool[] tempBooleanArray = new bool[playedThisRound.Length - 1];//reducing size of played this round array
                 Console.WriteLine("Playedthisround length: " + playedThisRound.Length + " \nThe Index: " + index.ToString());
                 tempBooleanArray = players[index].deletePlayerBool(playedThisRound, index);
                 playedThisRound = tempBooleanArray;
                 Console.WriteLine("New Player Array Size: " + players.Length);
                 Console.WriteLine("New Boolean Array Size: " + playedThisRound.Length);
             }
             if (index == players.Length - 1)
             {
                 index = 0;
                 numberOfPlayersWhoHavePlayedThisRound = 0;
             }
             if (players.Length == 1)
             {
                 roundOver = true;
             }
             index++;
             numberOfPlayersWhoHavePlayedThisRound++;
         }
            Console.WriteLine("WINNER:" + players[index].getName() + 
                "\nWins: " + players[index].getWins() + "\nArray Size: " + players.Length.ToString());

     }//end of while

     Console.WriteLine("Ending playGame - " 
           + "press any key to continue");
     Console.Read();
  }
       public bool playersAlreadyPlayed(bool[] thePlayer)
      {
          bool havePlayed = false;
          for (int plays = 0; plays < thePlayer.Length; plays++)
          {
              if (thePlayer[plays] == false)
              {
                  havePlayed = false;
              }
              else 
              {
                  havePlayed = true;
              }
          }
          return havePlayed;
      }

  static void Main(string[] args)
  {
     GuessingGame newGame = new GuessingGame();
     newGame.playGame();
  }
 }

}

这是播放器类

using System;

namespace GuessingGame
{

   class Player
   {

      private String name;
      private int winningNumber;
      private int guessesUsed;
      private int wins;
      private Random myWinningNumberSource;

      public Player(string newName, Random random)
      {
         name = newName;
         guessesUsed = 0;
         wins = 0;
         myWinningNumberSource = random;
         winningNumber = myWinningNumberSource.Next(1, 16);
      }


      public bool makeAGuess(int guessValue)
      {
          bool isWinner = false;//edit
         if (guessValue == winningNumber)
         {
            wins++;

            Console.WriteLine("Congradulations, You have guessed correct number!\n");
            Console.WriteLine("You have a total of " + wins + " wins!");
            Console.WriteLine("You have " + (3 - guessesUsed) + " guesses left!\n");
            winningNumber = myWinningNumberSource.Next(1, 16);
            isWinner = true; //edit

         }
         else
         {
            guessesUsed++;

            Console.WriteLine("Oh no! You have guessed incorretly!");
            Console.WriteLine("You have used " + guessesUsed + " and have " + (3 - guessesUsed) + " guesses left!");
            Console.WriteLine("HINT: You should have guessed " + winningNumber);
            isWinner = false; 


            if (guessesUsed > 3)
            {
                Console.WriteLine("Sorry you have Lost, Game Over");

            }

         }
         return isWinner; 
      } 

      public int getGuessesUsed()
      {
         return guessesUsed;
      }

      public string getName()
      {
         return name;
      }
      public int getWins()
      {
          return wins;
      }
      public Player[] getWinner(Player[] nPlayers)
      {
          int maxScore = 0; //edit
          Player[] winningPlayers;
          winningPlayers = new Player[5];
          for (int i = 0; i < nPlayers.Length; i++)
          {
              if (nPlayers[i].wins >= maxScore)
              {
                  winningPlayers[i].wins = nPlayers[i].getWins();
                  winningPlayers[i].name = nPlayers[i].getName();
              }
          }
          return winningPlayers;
      }
      public bool[] deletePlayerBool(bool[] playedThisRound, int removeIndex)//edit
      {
          bool[] newArray = new bool[playedThisRound.Length - 1];
          int tempIndex = 0;
          for (int i = 0; i < playedThisRound.Length; i++)
          {
              if (i != removeIndex)
              {
                  newArray[tempIndex++] = playedThisRound[i];
              }
          }
          return newArray;
      }
      public Player[] deletePlayerFromArray(Player[] nPlayers, int removeIndex)
      {
          Player[] newArray = new Player[nPlayers.Length - 1];
          int tempIndex = 0;
          for (int i = 0; i < nPlayers.Length; i++)
          {
              if (i != removeIndex)
              {
                  newArray[tempIndex++] = nPlayers[i];
              }
          }
          return newArray;
      }

   }
}

【问题讨论】:

  • 这是您应该使用调试器的地方。抛出异常的代码是哪一行?
  • 一般来说,IndexOutofRangeException 表示您正在尝试访问索引大于或等于数组长度的数组元素。记住:数组索引从零开始,不是一。
  • 你能告诉我们,这不是不撒谎的功课吗?
  • 看看它的作业,但我已经把它写到了我卡住的地步。我已经访问了 msdn 网站,但它没有告诉我在哪里。调试器告诉我我的程序在我的 GuessingGame 中的 if (players[index].getGuessesUsed() == 3) 查询中崩溃。我是 C# 新手,想学习。

标签: c# arrays debugging loops indexing


【解决方案1】:

这意味着您正在尝试访问比数组更大的索引。行内:

while(playedThisRound[index] == false)

你在使用索引之前没有检查边界,你的崩溃很可能就在那里。

【讨论】:

  • 好的,检查playedThisRound.Length的边界?
【解决方案2】:

这意味着您正在尝试访问一个索引高于数组限制的数组中的项目。

【讨论】:

    【解决方案3】:

    i 在 nPlayer 长度的范围内,而不是 0-4。

    public Player[] getWinner(Player[] nPlayers)
      {
          int maxScore = 0; //edit
          Player[] winningPlayers;
          winningPlayers = new Player[5];
          for (int i = 0; i < nPlayers.Length; i++)
          {
              if (nPlayers[i].wins >= maxScore)
              {
                  winningPlayers[i].wins = nPlayers[i].getWins();
                  winningPlayers[i].name = nPlayers[i].getName();
              }
          }
          return winningPlayers;
      }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2011-08-12
      • 2017-06-11
      • 2018-03-05
      • 2023-03-27
      • 1970-01-01
      • 2013-03-09
      • 2020-05-01
      相关资源
      最近更新 更多