source

C : typedef 구조명 {...}; VS typedef 구조{...} 이름

gigabyte 2022. 8. 27. 10:06
반응형

C : typedef 구조명 {...}; VS typedef 구조{...} 이름

제목에서 알 수 있듯이, 저는 다음과 같은 코드를 가지고 있습니다.

    typedef struct Book{
        int id;
        char title[256];
        char summary[2048];
        int numberOfAuthors;
        struct Author *authors;
    };


    typedef struct Author{
        char firstName[56];
        char lastName[56];
    };


    typedef struct Books{
        struct Book *arr;
        int numberOfBooks;
    };

gcc에서 다음 오류가 발생합니다.

bookstore.c:8:2: error: unknown type name ‘Author’
bookstore.c:9:1: warning: useless storage class specifier in empty declaration [enabled by default]
bookstore.c:15:1: warning: useless storage class specifier in empty declaration [enabled by default]
bookstore.c:21:2: error: unknown type name ‘Book’
bookstore.c:23:1: warning: useless storage class specifier in empty declaration [enabled by default]

다음과 같이 typedef를 변경해도 경고 및 오류는 발생하지 않습니다.

    typedef struct{
        char firstName[56];
        char lastName[56];
    } Author;

C Programming Language, 2차 에디션, 구글에서 몇 시간 동안 검색해도 첫 번째 구현이 왜 안 되는지 알 수 없습니다.

여기서 몇 가지 일이 일어나고 있습니다.우선, 다른 사람들이 말했듯이, 알 수 없는 타입에 대한 컴파일러의 불만은 사용하기 전에 타입을 정의해야 하기 때문일 수 있습니다.그러나 더 중요한 것은 (1) 구조 정의, (2) 구조 선언 및 (3) typedef의 3가지 구문을 이해하는 것입니다.

구조물을 정의할 때 구조물에 이름을 붙일 수도 있고 이름을 붙일 수도 있습니다(이름 없는 경우 즉시 사용해야 합니다). (아래에서 그 의미를 자세히 설명합니다.

struct Name {
   ...
};

구조 변수 선언에 사용할 수 있는 "구조 이름"이라는 유형을 정의합니다.

struct Name myNameStruct;

'하다'라는 됩니다.myNameStruct그것은 활자의 구조이다.struct Name.

구조체를 정의하는 동시에 구조 변수를 선언할 수도 있습니다.

struct Name {
   ...
} myNameStruct;

이전과, 과 called음음음음음음음음음음음음음음음 called called called called 라는 변수를 합니다.myNameStruct그것은 활자의 구조이다.struct Name...하지만 타입을 정의하는 동시에 실행한다. struct Name.
선언하기 위해 할 수 .

struct Name myOtherNameStruct;

여기서 typedef는 특정 이름을 가진 유형의 에일리어스를 지정하는 방법일 뿐입니다.

typedef OldTypeName NewTypeName;

를 지정하면 typedef를 사용할 NewTypeNameOldTypeNameC프로그래밍 언어에서 이것은 특히 구조물에 도움이 됩니다. 왜냐하면 이것은 그 유형의 변수를 선언할 때 "구조물"이라는 단어를 생략할 수 있고 구조체의 이름을 단순히 유형으로 취급할 수 있기 때문입니다(C++에서와 같이).다음은 구조물을 먼저 정의한 다음 구조물을 입력하는 예입니다.

struct Name {
   ...
};

typedef struct Name Name_t;

은 OldTypeName 입니다.struct Name은 NewTypeName 입니다.Name_t Name : 선언합니다 구조명 구조명

struct Name myNameStruct;

간단하게 쓸 수 있습니다.

Name_t myNameStruct;

또한 typedef는 구조 정의와 조합할 수 있으며, 코드에서는 다음과 같이 수행합니다.

typedef struct {
   ...
} Name_t;

이것은 구조물에 이름을 붙이는 동안에도 할 수 있지만, 이것은 불필요한 것입니다.

typedef struct Name {
   ...
} Name_t;

메모: 위의 구문에서는 "typedef"로 시작했으므로 문장 전체가typedefOldTypeName이 구조 정의일 가능성이 있습니다.따라서 컴파일러는 오른쪽 중괄호 뒤에 오는 이름을 NewTypeName으로 해석합니다.변수 이름이 아닙니다(typedef를 지정하지 않은 구문과 같기 때문에 이 경우 구조를 정의하는 동시에 구조 변수를 선언합니다).

게다가 typedef를 기술하고 Name_t를 종료하면 컴파일러가 " 내의 모든 것을 고려하기 때문에 사실상 INCOMPLETE typedef 문을 작성한 입니다.struct Name { ... }하지 않습니다." OldTypeName "typedef " NewTypeName " 입니다.이것이 컴파일러가 당신이 쓴 코드와 같이 만족하지 않는 이유입니다(하지만 당신이 무엇을 잘못했는지 잘 모르기 때문에 컴파일러의 메시지는 다소 애매합니다).

위에서 설명한 바와 같이 정의 시 스트럭트유형에 이름을 붙이지 않으면 변수를 선언하기 위해 스트럭트유형을 즉시 사용해야 합니다.

struct {
   ...
} myNameStruct;  // declares myNameStruct as a variable with this struct
                 // definition, but the definition cannot be re-used.

또는 typedef에서 이름 없는 구조 유형을 사용할 수 있습니다.

typedef struct {
   ...
} Name_t;

다음 구문은 실제로 작성했을 때 수행한 내용은 다음과 같습니다.

typedef struct{
   char firstName[56];
   char lastName[56];
} Author;

그리고 컴파일러는 기뻐했다.HTH

_t 접미사에 대한 코멘트/질문에 대하여:

_t 서픽스는 코드를 읽는 사람들에게 _t가 있는 기호 이름이 (변수 이름이 아닌) 유형 이름임을 나타내는 규칙입니다.컴파일러는 _t를 해석하거나 인식하지 않습니다.

C89, 특히 C99 표준도서관은 많은 유형을 정의하였고 그러한 유형의 이름에 _t를 사용하기로 결정하였다.예를 들어 C89 표준은 wchar_t, off_t, ptrdiff_t를 정의합니다.C99 표준에서는 uintptr_t, intmax_t, int8_t, uint_least16_t, uint_fast32_t 등 많은 추가 유형을 정의하고 있습니다.그러나 _t는 예약되어 있지 않으며 특별히 해석되어 있지 않으며 컴파일러에 의해 인식되어 있지 않으며 C에서 (typedef를 통해) 새로운 유형을 정의할 때 따르는 것이 좋은 규칙일 뿐입니다.C++ 에서는, 예를 들면 MyNewType(C 의 my_new_type_t 가 아니고, MyNewType 이라고 하는 표기법을 사용하고 있는 사람이 많습니다.HTH

은 '하다' 입니다.typedef음음음같 뭇매하다

typedef old_type new_type

첫 번째 시도에서는struct Book타이핑하고 안 하다 Book즉, 데이터 타입은struct Book가 아니라Book.

두 번째 양식에서는 올바른 구문을 사용했습니다.typedef컴파일러는 다음과 같은 유형을 인식합니다.Book.

변수를 실제로 선언하는 시기를 명확히 하여 추가합니다.

struct foo {
   int a;
} my_foo;

정의하다foo즉시 변수를 선언합니다.my_foostruct footype, 즉 이렇게 사용할 수 있습니다.my_foo.a = 5;

단, 왜냐하면typedef구문은 다음과 같습니다.typedef <oldname> <newname>

typedef struct bar {
   int b;
} my_bar;

변수를 선언하지 않음my_bar입입 of struct bar,my_bar.b = 5; 불법입니다.대신 새로운 이름을 붙이고 있습니다.struct bar를 치다my_bar할 수 있습니다.struct bar를 치다my_bar음음음같 뭇매하다

my_bar some_bar;

다른 답변은 모두 정확하고 유용하지만 필요한 만큼 더 길 수도 있습니다.다음을 수행합니다.

typedef struct Book Book;
typedef struct Books Books;
typedef struct Author Author;

struct Book {
    ... as you wish ...
};

struct Author {
    ... as you wish ...
};

struct Books {
    ... as you wish ...
};

''를 정의할 수 있습니다.struct기타 포인터만 포함하는 경우 임의의 순서로 표시됩니다.struct의 discriptions

Book을 정의하기 전에 Author를 정의하기만 하면 됩니다.

Book에서 Author를 사용하므로 사전에 정의해야 합니다.

이해하는데 도움이 될 것 같아요.http://www.tutorialspoint.com/cprogramming/c_typedef.htm

bookstore.c:8:2: error: unknown type name ‘Author’
bookstore.c:21:2: error: unknown type name ‘Book’

이것들은 사용하기 전에 정의해야 하기 때문에 생산됩니다.구조 "Author"와 "Books"를 구조 "Book" 위로 이동합니다.이거면 해결될 거야.

또, 문제가 발생하고 있는 경고에 의해서도, 「typedef structure Author」가 불필요하다고 컴파일러가 특정됩니다.이는 사용자가 구조에 올바르게 입력되어 있지 않기 때문입니다.따라서 컴파일러가 "읽을 수 있는" 유용한 정보가 없기 때문입니다.

이미 이 형식으로 대답해야 한다는 것을 알고 계시기 때문에

typedef struct {
 ...
 ... 
 ...
} struct-name;

계속 그렇게 해

언급URL : https://stackoverflow.com/questions/17720223/c-typedef-struct-name-vs-typedef-struct-name

반응형