C에서는 함수에서 배열을 반환 할 수 없지만 배열에 대한 포인터를 반환한다는 것을 알고 있습니다. 그러나 structs
배열이 포함되어 있어도 함수로 반환 할 수 있는 특별한 점이 무엇인지 알고 싶습니다 .
struct
래핑으로 인해 다음 프로그램이 유효한 이유는 무엇 입니까?
#include <stdio.h>
struct data {
char buf[256];
};
struct data Foo(const char *buf);
int main(void)
{
struct data obj;
obj = Foo("This is a sentence.");
printf("%s\n", obj.buf);
return 0;
}
struct data Foo(const char *buf)
{
struct data X;
strcpy(X.buf, buf);
return X;
}
답변
동일한 질문을하는 더 좋은 방법은 “배열에 대해 특별한 점”이 될 것입니다 struct
. s가 아니라 특수 처리가 연결된 배열이기 때문입니다 .
포인터로 배열을 전달하고 반환하는 동작은 C의 원래 구현으로 거슬러 올라갑니다. 배열은 포인터에 대해 “감쇠”하여 특히 언어를 처음 접하는 사람들 사이에서 많은 혼란을 야기합니다. 반면에 구조체는 int
s, double
s 등과 같은 내장 유형처럼 작동합니다 . 여기에는 복사되지 않는 유연한 배열 멤버를struct
제외하고에 포함 된 모든 배열이 포함됩니다 .
답변
우선, 인용하다 C11
, §6.8.6.4 장, return
성명 ( 내 강조 )
만약
return
식이 문이 실행되면 식 의 값이 함수 호출 식의 값으로 호출자에게 반환 됩니다.
구조 값 이 반환 되기 때문에 구조 변수 반환이 가능하고 정확합니다 . 이는 모든 기본 데이터 유형을 반환하는 것과 유사합니다 ( int
예 :를 반환 ).
반면 에를 사용하여 array 를 반환하면 return <array_name>
기본적으로 배열 NOTE 의 첫 번째 요소 주소를 반환합니다.이 주소 는 배열이 호출 된 함수에 대해 로컬 인 경우 호출자에서 유효하지 않게됩니다. 따라서 이러한 방식으로 배열을 반환하는 것은 불가능합니다.
그래서, TL; DR은 , 아무것도가 특별 와 struct
의, 전문가에 배열 .
노트:
C11
다시 인용 , §6.3.2.1 장 ( 내 강조점 )
그것의 오퍼랜드 인 경우를 제외하고
sizeof
오퍼레이터의_Alignof
조작 또는 단항&
연산자, 또는 어레이를 초기화하는 데 사용되는 캐릭터 문자이다 형 갖는 식 ‘유형의 배열을’ 유형의 표현으로 변환된다 ‘ 유형에 대한 포인터 ” 는 배열 객체의 초기 요소를 가리키며 lvalue가 아닙니다. […]
답변
struct
유형 에 대해 특별한 것은 없습니다 . 배열 유형 에 대해 함수에서 직접 반환되는 것을 방지하는 특별한 것이 있다는 것입니다.
struct
발현 다른 배열이 아닌 형태의 식처럼 취급되고; 의 값 으로 평가됩니다 struct
. 그래서 당신은 같은 일을 할 수 있습니다
struct foo { ... };
struct foo func( void )
{
struct foo someFoo;
...
return someFoo;
}
표현식 은 객체 someFoo
의 값 으로 평가됩니다 struct foo
. 객체의 내용은 함수에서 반환됩니다 (해당 내용에 배열이 포함되어 있더라도).
배열 표현식은 다르게 처리됩니다. sizeof
또는 단항 &
연산자 의 피연산자 가 아니거나 선언에서 다른 배열을 초기화하는 데 사용되는 문자열 리터럴이 아닌 경우 식은 “array of T
” 유형 에서 “pointer to”로 변환 ( “감쇠”) 됩니다.T
” . , 식의 값은 첫 번째 요소의 주소입니다.
따라서 배열 표현식에 대한 모든 참조는 자동으로 포인터 값으로 변환되기 때문에 함수에서 값 으로 배열 을 반환 할 수 없습니다 .
답변
구조체는 기본적으로 데이터 멤버를 public으로하므로 구조체의 경우 main의 데이터에 액세스 할 수 있지만 클래스의 경우에는 액세스 할 수 없습니다. 따라서 구조체 래핑이 유효합니다.
답변
