728x90
핵심은 List는 값을 참조해서 가져온다는 것이다.
참조하는 본체를 하나로만 두고 본체의 값을 변경한다면, List는 0~List.Count 값까지 전부 똑같이 변하게 된다.
아래 예시이다.
List<string[]> 리스트에 스트링배열을 넣어서 선언을 해주었는데
string[] cardMemory라는 변수로 while을 돌려서 List에 계속 값을 넣어주었다.
중간에 프린트를 찍어보았을때는 분명 값이 랜덤으로 들어간것으로 확인이 되었었는데
그런데 마지막에 출력시에는 같은값이 14개가 프린트가 되었다.
나는 랜덤값으로 계속 cardMemory를 초기화 해준것으로 생각했으나 그것이 아니었다.
cardMemory를 초기화 해주기 위해서는 new를 이용하여 새로 할당해주어야 한다.
if (!isDuplicate)
{
cardDeck.Add(cardMemory);
cardMemory = new string[2];
}
이 부분이 핵심이다.
그렇게 하지 않는다면 List는 값을 변수에서 참조하여 가져오기 때문에 0번부터 14번 인덱스까지 cardMemory의 값이 변경될때마다
List에 할당한 값 전체가 변경되게 되어 연속해서 똑같은 값이 출력되는 오류를 범할 수 있다.
아래는 오류코드 이다.
//using System;
//namespace MyApp
//{
// internal class Program
// {
// static void Main(string[] args)
// {
// string[] cardNumber = new string[13] { "A", "2", "3", "4", "5", "6", "7", "8", "9", "10", "J", "Q", "K" };
// string[] cardMark = new string[4] { "♠", "♥", "♣", "◆" };
// string[] cardMemory = new string[2];
// Random rand = new Random();
// List<string[]> cardDeck = new List<string[]>();
// int random1 = default;
// int random2 = default;
// //cardMemory[0] = cardNumber[1];
// //cardMemory[1] = cardMark[0];
// //cardDeck.Add(cardMemory);
// //cardDeck.Add(cardMemory);
// //cardDeck.Add(cardMemory);
// //cardDeck.Add(cardMemory);
// //Console.WriteLine(cardDeck[3][0]);
// while (true)
// {
// int j = 0;
// int k = 0;
// random1 = rand.Next(0, 13);
// random2 = rand.Next(0, 4);
// cardMemory = new string[2];
// cardMemory[0] = cardNumber[random1];
// cardMemory[1] = cardMark[random2];
// ////중복조건
// //cardDeck.Add(cardMemory);
// //while (true)
// //{
// // if((cardDeck[k][0] == cardMemory[0]) && (cardDeck[k][1] == cardMemory[1]))
// // {
// // random1 = rand.Next(0, 13);
// // random2 = rand.Next(0, 4);
// // cardMemory[0] = cardNumber[random1];
// // cardMemory[1] = cardMark[random2];
// // }
// // else if(cardDeck.Count == k)
// // {
// // break;
// // }
// // k++;
// //}
// if (cardDeck.Count == 14)
// {
// break;
// }
// for (int i = 0; i < cardDeck.Count + 1; i++)
// {
// if (cardDeck.Count == 14)
// {
// break;
// }
// if (j == cardDeck.Count)
// {
// cardDeck.Add(cardMemory);
// //Console.WriteLine(cardMemory[0] + cardMemory[1]);
// break;
// }
// //if ((cardDeck[i][0] != cardMemory[0]) || (cardDeck[i][1] != cardMemory[1]))
// //{
// // j++;
// //}
// //else if (cardDeck[i] == cardMemory)
// //{
// // break;
// //}
// j++;
// //중복조건
// if ((cardDeck[i][0] == cardMemory[0]) && (cardDeck[i][1] == cardMemory[1]))
// {
// }
// }
// }
// //Console.WriteLine(cardDeck[5][0] + cardDeck[5][1]);
// //Console.WriteLine();
// for (int i = 0; i < cardDeck.Count; i++)
// {
// Console.WriteLine(cardDeck[i][0] + cardDeck[i][1]);
// }
// }//Main
// }//class
//}//namespace
수정한 코드
using System;
using System.Collections.Generic;
namespace MyApp
{
internal class Program
{
static void Main(string[] args)
{
string[] cardNumber = new string[13] { "A", "2", "3", "4", "5", "6", "7", "8", "9", "10", "J", "Q", "K" };
string[] cardMark = new string[4] { "♠", "♥", "♣", "◆" };
string[] cardMemory = new string[2];
Random rand = new Random();
List<string[]> cardDeck = new List<string[]>();
while (cardDeck.Count < 14)
{
int random1 = rand.Next(0, 13);
int random2 = rand.Next(0, 4);
cardMemory[0] = cardNumber[random1];
cardMemory[1] = cardMark[random2];
bool isDuplicate = false;
foreach (string[] card in cardDeck)
{
if (card[0] == cardMemory[0] && card[1] == cardMemory[1])
{
isDuplicate = true;
break;
}
}
if (!isDuplicate)
{
cardDeck.Add(cardMemory);
cardMemory = new string[2];
}
}
foreach (string[] card in cardDeck)
{
Console.WriteLine(card[0] + card[1]);
}
}
}
}
728x90
'프로그래밍 > C#' 카테고리의 다른 글
[C#] (글 수정필요) Partial 클래스, Extended 메소드 (0) | 2023.06.21 |
---|---|
[C#] 박싱,언박싱 / 업캐스팅, 다운캐스팅 (0) | 2023.06.20 |
[C#] 프로퍼티, 왜 사용하는거지? (0) | 2023.06.18 |
foreach 이용 (0) | 2023.06.15 |
C# 컬렉션(Collection_List, Dictionary, Stack, Queue, ArrayList) (0) | 2023.06.15 |