Các phần tử mảng của các thành viên struct và struct


8

Tôi muốn hỏi về một khai báo struct trong C. Ví dụ:

struct Person
{
    char name[50];
    int citNo;
    float salary;
} prsn[20];

Không gì [20]làm gì? Nó có nghĩa là gì? Có giới hạn tên đến 20 (từ 50) hoặc giới hạn prsntừ prsn[1]đến prsn[20]?

Và nếu tôi viết mã như thế này:

struct Person
{
    char name[50];
    int citNo;
    float salary;
};
struct Person prsn[20];

Liệu nó có làm điều tương tự?


3
Chúng giống nhau: cả hai đều khai báo một mảng các 20phần tử loạistruct Person
LP

Nó giống như int prsn[20];ngoại trừ với struct Person thay vì int
MM

Câu trả lời:


8

[20] làm gì? Nó có nghĩa là gì?

Các ý kiến ​​dưới đây cho thấy danh pháp chung cho các phần của cấu trúc của bạn :

struct Person {    //struct name (Person)
    char name[50]; // \
    int citNo;     //  --struct members 
    float salary;  // /
} prsn[20];        // instance of struct Person array

Điều này [20]chỉ ra rằng ví dụ struct Personnày là một mảng gồm 20 bộ sưu tập riêng biệt của 3 thành viên. Mỗi phần tử của mảng có thể được truy cập bằng cách sử dụng ký hiệu mảng. Ví dụ: trong một vòng lặp:

int main(int argc, char *argv[])
{
    for(int i=0;i<20;i++)// note i goes from 0 to 19
    {
        //.....
        //assuming members have been populated
        printf( "%d)\nName is: %d\ncitNo is: %d salary is: %f\n\n", prsn[i].name, prsn[i].citNo, prsn[i].salary);
    }

    return 0;
}

[20] có giới hạn tên thành 20 (từ 50) hoặc giới hạn prsntừ prsn[1]đến prsn[20]không?

Các thành viên name[50]xác định một mảng 50 char. Kích thước của nó không bị ảnh hưởng theo bất kỳ cách nào bởi [20]chỉ mục được sử dụng để định kích thước mảng của struct. tức là như bạn đã định nghĩa, có 20 trường hợp prsn, mỗi trường hợp chứa 3 thành viên : char [50], intfloat. Và theo định nghĩa của bạn, 20 trường hợp được tạo bởi [20]cho phép mảng được truy cập với các giá trị chỉ mục từ đó 0đến 19. (Xem hình minh họa vòng lặp ở trên.)

EDIT để giải quyết câu hỏi OP trong ý kiến:

Và tôi phải làm gì nếu tôi muốn làm cho các yếu tố không giới hạn?

Nếu bạn muốn sử dụng dấu ngoặc rỗng, ( []) định nghĩa phải bao gồm danh sách khởi tạo cấu trúc . Ví dụ:

... } prsn[] = {{"Bill", 1, 23000.00}, {"John", 2, 45000.00}, ...};  

Nếu kích thước của mảng cấu trúc không được biết đến tại thời điểm biên dịch và cần được định kích thước theo thông tin chỉ có sẵn trong thời gian chạy, thì có thể sử dụng cấp phát bộ nhớ động hoặc VLA . Đầu tiên, đối với bộ nhớ động, thay vì xác định bằng ký hiệu mảng, hãy tạo một thể hiện con trỏ:

... } *prsn;  

Sau đó, trong một hàm, sử dụng callochoặc mallocđể tạo bộ nhớ cho 1000 trường hợp:

int someFunction(void)
{
    prsn = calloc(1000, sizeof(struct Person));
    if(prsn)
    {
        // Use instances of prsn
        // free when finished
        free(prsn);
    }

Đối với VLA, các thể hiện được tạo phải có phạm vi cục bộ. Vì vậy, bên trong một chức năng ở đâu đó, hãy làm điều này:

int someFunction(int sizeOfStruct)
{
    struct Person newPerson[sizeOfStruct] = {0};

Lưu ý phương pháp này không yêu cầu giải phóng bộ nhớ liên quan đến newPerson


Mặc dù với số lượng người không giới hạn, OP có thể sử dụng danh sách được liên kết tốt hơn hoặc có thể là một mảng các con trỏ tới Person, đặc biệt là nếu số lượng Người có thể thay đổi trong thời gian chạy. Nếu không, bạn sẽ mất rất nhiều thời gian để sao chép các thành viên hiện có, bằng tay hoặc bằng một cuộc gọi đến realloc.
jamesqf

9

Hai đoạn mã trên là tương đương.

Trong phần đầu tiên, bạn xác định struct Personvà định nghĩa prsnlà một mảng gồm 20 phần tử của cấu trúc đó cùng một lúc. Trong lần thứ hai, trước tiên bạn xác định cấu trúc sau đó xác định riêng mảng.

Trong C, các chỉ mục mảng bắt đầu từ 0, vì vậy trong cả hai trường hợp, prsnmảng chứa các phần tử được lập chỉ mục từ 0 đến 19. Điều này không ảnh hưởng đến kích thước của namethành viên, là mảng 50 phần tử. Bạn có một mảng 20 struct Person, mỗi mảng chứa một mảng 50 phần tử charđược gọi name.

Về việc làm cho kích thước mảng không giới hạn, một mảng phải có kích thước, được chỉ định rõ ràng giữa []hoặc ngầm định thông qua danh sách khởi tạo. Kích thước có thể là một biến tuy nhiên một mảng như vậy không thể được xác định ở phạm vi tệp và biến kích thước phải được gán một giá trị trước đó.


1
Vậy có nghĩa là một mảng prsn [0] thành prsn [19] phải không? Và tôi phải làm gì nếu tôi muốn làm cho các yếu tố không giới hạn? prsn [n] hoặc prsn [] hoặc chỉ prsn?
abw1904

2
@ abw1904 Một mảng phải có kích thước, được chỉ định rõ ràng giữa []hoặc ngầm định thông qua danh sách khởi tạo. Kích thước có thể là một biến tuy nhiên một mảng như vậy không thể được xác định ở phạm vi tệp và biến kích thước phải được gán một giá trị trước đó.
dbush

1
@ abw1904 Để mã hóa "mảng kích thước thay đổi", bạn nên xem Danh sách liên kết. Rõ ràng là sẽ không giới hạn, nhưng nó có thể phát triển khi chạy
LP


0

[20] chỉ ra rằng trường hợp struct Personnày là một mảng gồm 20 bộ sưu tập riêng biệt của 3 thành viên. Mỗi phần tử của mảng có thể được truy cập bằng cách sử dụng ký hiệu mảng. Trong C, các chỉ mục mảng bắt đầu từ 0, vì vậy mỗi lần prsnbắt đầu từ 0 đến 19. Bạn có thể kiểm tra trang web này về Cấu trúc trong C

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.