증분 피연산자로 l 값이 필요
gcc 4.4.4
내가 뭘 잘못하고 있는 거지?
char x[10];
char y[] = "Hello";
while(y != NULL)
*x++ = *y++;
어떤 조언이든 감사드립니다.
x++
의 짧은 형태입니다.x = x + 1
.하지만,x
여기 배열이 있고 배열의 주소를 수정할 수 없습니다.당신 변수의 경우도 마찬가지입니다.y
너무.
배열을 증가시키는 대신 정수를 선언할 수 있습니다.i
그리고 그 다음에 접근하는 증가를 합니다.i
배열의 제 인덱스입니다.
char x[10], y[5] = "Hello";
int i = 0;
while (y[i] != 0)
{
x[i] = *y[i];
i++;
}
x[i] = 0;
"어레이는 포인터"라는 일반적인 오해에 빠졌을 가능성이 높습니다. 즉, 배열을 정의할 때 실제로 얻는 것이 어딘가에 할당된 메모리 블록을 가리키는 일반적인 포인터입니다.코드에서 해당 포인터를 증가시키려고 시도하고 있습니다.
실제로 배열은 포인터가 아니기 때문에 코드가 "작동"하지 않습니다.배열은 배열입니다.배열을 증분할 수 없습니다.C 언어로 "배열 증가"와 같은 연산은 없습니다.사실 C에 있는 배열 자체는 수정할 수 없는 l 값입니다.C에는 배열 자체를 수정할 수 있는 작업이 없습니다(개별 요소만 수정 가능).
실제로 시도하는 "슬라이딩 포인터" 기법을 사용하여 배열을 횡단하려면 포인터를 명시적으로 생성하고 배열의 시작 요소를 가리키도록 해야 합니다.
char *px = x;
char *py = y;
그런 다음 원하는 만큼 이 포인터를 증가시킬 수 있습니다.
C의 배열은 사실 포인터이지만, 상수 포인터이므로 선언 후에는 값을 변경할 수 없습니다.
int arr[] = {1, 2, 3};
// arr is declared as const pointer.
(arr + 1)
가능합니다만arr++
가능하지 않습니다. 왜냐하면arr
주소가 일정하기 때문에 다른 주소를 저장할 수 없습니다.
char x[10];
char y[] = "Hello";
char *p_x = &x[0];
char *p_y = &y[0];
while(*p_y != '\0') *p_x++ = *p_y++;
배열 주소를 수정할 수 없으므로 다음과 같이 수행합니다.x++
그리고.y++
당신의 코드에서) 그리고 당신은 포인터 주소를 수정할 수 있습니다. 저는 배열의 주소를 개별 포인터로 복사한 다음 증가시켰습니다.
원하신다면 표기를 줄일 수 있으실 거라고 확신하지만, 요점을 이해하셨으면 좋겠습니다.
x
그리고.y
포인터가 아닌 배열입니다.
증분식과 같은 대부분의 식 컨텍스트에서 포인터로 붕괴되지만 l 값이 아닌 r 값으로 붕괴되며 증분 연산자를 l 값에만 적용할 수 있습니다.
대개 포인터처럼 배열합니다.
배열을 수정할 수 없다는 것만 기억하세요!
그리고.y++
이다.y = y + 1
.
char y[] = "Hello";
그래서 당신은 배열을 수정합니다.y++
!!
그것은 생산할 것입니다.error: lvalue required as increment operand
.
당신이 둘 다 정의했으니깐x
그리고.y
배열로 수정할 수 없습니다.한 가지 가능성은 포인터를 대신 사용하는 것입니다.
char x[10];
char *xx = x;
char *y = "Hello";
while (*y != '\0')
*xx++ = *y++;
사용자의 종료 조건도 수정했습니다. 포인터가NULL
끈의 끝에 닿았다고 해서요
배열 이름을 수정할 수는 없지만 다음은?argv++
인에f(int argv[])
?
p99의 K&R에서 인용한 "배열 이름은 변수가 아닙니다. 구조는 다음과 같습니다.a = pa
그리고.a++
배열의 이름이 초기 요소의 위치에 대한 동의어임을 나타내는 "religal".
그러나 함수 매개 변수에서 왜func(char *argv[])
, 할 수 있습니다argv++
에도 불구하고argv
는 배열 이름입니다.
그리고 인.int *a[10]
, 우리는 할 수 없습니다.a++
맘에 들다argv++
.
배열의 이름은 초기 요소의 위치와 동의어입니다. ---K&R
arrayname++
불법입니다.
함수 파라미터에서와 에서 :char *argv[]
, 와 같습니다char **argv
.type *arrayname_para[]
in parameter 는 의 또다른 동의어입니다.type **arrayname_para
.
배열은 할당된 메모리의 정적 연속 블록입니다.배열 이름은 첫 번째 블록 메모리에 대한 불변 참조입니다.(배열의 이름으로 참조) 주소를 증가시키려 하면 다른 메모리 위치가 손실(차등이라고 하는 것이 더 좋습니다)됩니다.준비가 되어 있다고 가정합니다.
int p[]={10,20,30}
여기서 p(설계 기준)는 인덱스 0을 나타냅니다.우리가 증가시키는 어딘가에서 다음과 같이 말합니다.p++
증분이 허용된다고 가정하면 인덱스 1을 p에서 p로 점하게 됩니다.이제 생각해보니깐p[1]=?
p[1]
그러면 현재 위치의 오른쪽에 있는 한 곳의 값을 역참조하는 것으로 해석됩니다.
또는 위치p[2]
원래 배열일 경우.
이 작업을 반복하면 곧 배열 인덱스를 추적하는 것이 매우 번거로울 것입니다.
따라서 이러한 사고를 방지하기 위해 배열 이름(lvalue) 주소는 불변입니다.또 다른 개념은 워드 어드레싱과 바이트 어드레싱입니다:-
C의 문자 배열( 문자열)은 단어 주소 지정 대신 바이트 주소 지정이 가능합니다.그래서 만약 우리가 배열을 가지고 있다면,
inta[]={10,20,30}
printf("%d",*(a+1)) //Ouput:20 (int is word addressable)
printf("%d",*(++a)) // Error: Array references are immutable
int* cpya=a;
printf("%d",*(++cpya)) /* Output:20 (cpy is not array reference but a copy. Hence is Mutable) */
char b[]="Hello"
printf("%c",*(++b)) // Error : Array references are immutable
printf("%c",*(b+1)) /* undefined_behavior as character Array(strings) are byte addressable and not word addressable */
printf("%c",*(b+sizeof(char)*1)) // Output :e (It's byte addressable).
To understand more I suggest reading the official docs for B 프로그래밍 언어 at
[B Reference Manual- Data Objects][1]
배열은 일정한 포인터입니다.바꿀 수 없어요.
int q;
int *const p = &q;
p = NULL; // this is not allowed.
언급URL : https://stackoverflow.com/questions/3364445/lvalue-required-as-increment-operand
'code' 카테고리의 다른 글
jQuery 상위 양식 찾기 (0) | 2023.10.25 |
---|---|
Woocommerce에서 특정 텍스트 변경 또는 번역 (0) | 2023.10.25 |
Azure DevOps - PowerShell 스크립트에서 변수 설정 및 사용 (0) | 2023.10.20 |
도커 파일에 인수를 전달하는 방법? (0) | 2023.10.20 |
(2.x로 업그레이드하는 대신) nuget을 jQuery 1.9.x/1.x 경로로 유지할 수 있습니까? (0) | 2023.10.20 |