VB.NET 코드를 C #으로 마이그레이션 할 때 for 루프가 다르게 작동하는 이유는 무엇입니까?


87

Visual Basic에서 C #으로 프로젝트를 마이그레이션하는 for중이며 사용중인 루프가 선언되는 방식을 변경해야했습니다 .

VB.NET에서 for루프는 다음과 같이 선언됩니다.

Dim stringValue As String = "42"

For i As Integer = 1 To 10 - stringValue.Length
   stringValue = stringValue & " " & CStr(i)
   Console.WriteLine(stringValue)
Next

출력되는 내용 :

42 1
42 1 2
42 1 2 3
42 1 2 3 4
42 1 2 3 4 5
42 1 2 3 4 5 6
42 1 2 3 4 5 6 7
42 1 2 3 4 5 6 7 8

C #에서 for루프는 다음과 같이 선언됩니다.

string stringValue = "42";

for (int i = 1; i <= 10 - stringValue.Length; i ++)
{
   stringValue = stringValue + " " + i.ToString();
   Console.WriteLine(stringValue);
}

그리고 출력 :

42 1
42 1 2
42 1 2 3

이것은 분명히 정확하지 않으므로 코드를 약간 변경하고 문자열 길이를 유지하는 정수 변수를 포함해야했습니다.

아래 코드를 참조하십시오.

string stringValue = "42";
int stringValueLength = stringValue.Length;

for (int i = 1; i <= 10 - stringValueLength; i ++)
{
   stringValue = stringValue + " " + i.ToString();
   Console.WriteLine(stringValue);
}

그리고 출력 :

42 1
42 1 2
42 1 2 3
42 1 2 3 4
42 1 2 3 4 5
42 1 2 3 4 5 6
42 1 2 3 4 5 6 7
42 1 2 3 4 5 6 7 8

이제 내 질문 은 루프가 발생할 때마다 문자열의 길이가 변경 되더라도 루프 의 stringValue.Length조건을 사용하여 Visual Basic 측면에서 Visual Basic이 C #과 어떻게 다른지에 대해 해결합니다 for. 반면 C # stringValue.Length에서는 for루프 조건 에서 사용 하면 루프가 발생할 때마다 초기 문자열 값이 변경됩니다. 왜 이런거야?


7
Microsoft 는 귀하의 문제가 무엇인지 명확하게 설명합니다.
Codexer 2018 년

39
@ Çöđěxěŕ : 그만해주세요. 문맥에 관계없이 제목에서 태그를 로봇으로 제거하는 것이 도움이된다면 웹 사이트에서 그렇게 할 것입니다.
Ry-

11
Çöđěxěŕ @ 당신은 그것에 대해 몇 가지 정보를 찾을 수 있습니다 여기에
푸쉬킨

35
@ Çöđěxěŕ 두 게시물이 서로 모순되지 않는다고 생각합니다. 요점은 "이 것에 대한 질문-태그"와 같이 제목에 어색하게 태그를 붙이지 마십시오. 그러나 제목이 태그를 포함하는 완전한 문장이면 때때로 괜찮습니다. "마이그레이션 할 때 for 루프가 다르게 작동하는 이유"는 너무 일반적인 제목처럼 느껴집니다.
푸쉬킨

26
@ Çöđěxěŕ "VB.NET 코드를 C #으로 마이그레이션"은 제목에 유용한 정보를 추가하는 완전한 문구입니다. 선명도를 떨어 뜨리는 편집을하지 마십시오. 바라건대, 그 개념은 우리가 그것을 백업하기 위해 메타 포스트가 필요하지 않을만큼 충분히 상식적인 것입니다.
jpmc26

답변:


115

C #에서 루프 경계 조건은 각 반복에서 평가됩니다. VB.NET에서는 루프 진입시에만 평가됩니다.

따라서 질문의 C # 버전 stringValue에서는 루프에서 길이 가 변경되므로 최종 루프 변수 값이 변경됩니다.

VB.NET에서는 최종 조건이 포괄적이므로 C # <=대신 사용 합니다 <.

C #의 종료 조건 평가에는 변하지 않지만 계산하는 데 비용이 많이 들더라도 루프 전에 한 번만 계산해야한다는 결론이 있습니다.


답장을 보내 주셔서 감사합니다. <=이제을 사용 하면 VB 코드와 동일한 출력을 반복하고 사용할 수 있음을 알게 되었습니다. 그러나, 정수 변수를 선언해야하는데 그럴 필요가 없었던 이유를 아는 데 더 관심 VB이 있습니다. 동일한 출력을 표시하도록 내 질문을 업데이트하겠습니다.
slee423

@ slee423 이유는 내 대답의 첫 번째 문장에 나와 있습니다. stringValue루프에서 길이 가 변경되므로 최종 루프 변수 값이 변경됩니다.
Andrew Morton

1
사과드립니다. 답변 해 주셔서 감사합니다. 더 자세히 설명 해주셔서 감사합니다.
slee423

1
@ slee423 나는 그것이 실제로 그것을 명확히하기 때문에 대답에 추가했습니다.
Andrew Morton

22

이제 내 질문은 루프가 발생할 때마다 문자열 길이가 변경 되더라도 for 루프에서 stringValue.Length 조건을 사용하여 VB 측면에서 VB가 C #과 어떻게 다른지에 대해 해결합니다.

VB.NET 문서 에 따르면 :

counter루프 내에서 while 값을 변경하면 코드를 읽고 디버그하기가 더 어려울 수 있습니다. 의 값을 변경 start, end또는 step루프가 처음 입력 할 때 결정되었다 반복 값에 영향을주지 않습니다.

따라서의 값은 To 10 - stringValue.Length한 번 평가되고 루프가 종료 될 때까지 재사용됩니다.

그러나 C #의 for 문을 살펴보십시오 .

(가) 경우 for_condition본이나 평가 수율 아닌 경우 true, 제어는 삽입 명령문에 전송된다. 제어가 포함 된 문의 끝점에 도달하면 (아마도 continue 문의 실행에서)의 식 ( for_iterator있을 경우)이 순서대로 평가 된 다음 for_condition단계의 평가부터 시작하여 다른 반복이 수행 됩니다. 위.

이는 기본적으로 조건 ; i <= 10 - stringValueLength;이 매번 다시 평가 된다는 것을 의미합니다 .

따라서 본 것처럼 코드를 복제하려면 루프를 시작하기 전에 C #에서 최종 카운터를 선언해야합니다.


11

예제를 더 이해하기 쉽게 만들기 위해 두 for 루프 를 모두 C # while 루프 로 변환합니다 .

VB.NET

string stringValue = "42";

int min = 1;
int max = 10 - stringValue.Length;
int i = min;
while (i <= max)
{
    stringValue = stringValue + " " + stringValue.Length.ToString();
    Console.WriteLine(stringValue);
    i++;
}

씨#

string stringValue = "42";

int i = 1;
while (i <= 10 - stringValue.Length)
{
    stringValue = stringValue + " " + stringValue.Length.ToString();
    Console.WriteLine(stringValue);
    i++;
}

차이점은 다음과 같습니다.

VB.NET 은에 대한 최대 값을 캐시 i하지만 C #은 매번이를 다시 계산합니다.


2
루프를 while으로 변환 할 필요가 없습니다.
Panagiotis Kanavos 2010 년

10
처음부터 이해하는 데 도움이 for loops되었고 훨씬 더 이해하기 쉽다고 생각합니다. 이것이 while loops이해를 돕기 위해 에서 예제를 '번역'한 이유 입니다.
Maxime Recuerda

7

forin VB는 forin C # (또는 다른 C와 유사한 언어)과 다른 의미 이기 때문에

VB에서 for명령문은 특히 한 값에서 다른 값으로 카운터를 증가시킵니다.

C, C ++, C # for등에서이 명령문은 단순히 세 가지 표현식을 평가합니다.

  • 첫 번째 표현식은 일반적으로 초기화입니다.
  • 두 번째 표현식은 각 반복이 시작될 때 평가되어 최종 조건이 충족되었는지 여부를 판별합니다.
  • 세 번째 표현식은 일반적으로 증분자인 각 반복이 끝날 때 평가됩니다.

VB에서는 터미널 값에 대해 테스트 할 수 있고 각 반복에서 증가 할 수있는 숫자 변수를 제공 해야합니다.

C, C ++, C # 등에서 세 가지 식은 최소한으로 제한됩니다. 조건식은 참 / 거짓 (또는 C, C ++에서 0이 아닌 정수)으로 평가되어야합니다. 초기화를 전혀 수행 할 필요가 없습니다. 값의 범위에 관계없이 모든 유형을 반복하거나, 복잡한 구조에 대해 포인터 또는 참조를 반복하거나, 아무것도 반복하지 않을 수 있습니다.

따라서 C # 등에서는 각 반복에서 조건식을 완전히 평가해야하지만 VB에서는 반복기의 터미널 값을 처음에 평가해야하며 다시 평가할 필요가 없습니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.