C语言中:将结构体名写在函数前面表示这个函数返回一个该结构体类型的值

发布于:2025-07-05 ⋅ 阅读:(15) ⋅ 点赞:(0)

 假设有一个表示二维点的结构体:

struct Point {
    int x;
    int y;
};

然后,定义一个函数,该函数返回一个Point结构体:

struct Point create_point(int x, int y); 

struct Point create_point(int x, int y) {
    struct Point p;
    p.x = x;
    p.y = y;
    return p;  // 返回结构体实例
}

可以这样使用

int main() {

    struct Point p1 = create_point(3, 4);
    printf("Point: (%d, %d)\n", p1.x, p1.y);
    return 0;
}

注!!

在C语言中,返回结构体是合法的,但是要注意返回结构体会发生值拷贝(即整个结构体的内容会被复制到接收的变量中)。如果结构体很大,可能会有效率问题。

因此:在这种情况下,可以考虑返回结构体指针(但要注意指针指向的内存生命周期)或者使用输出参数(通过指针传入结构体地址,在函数内填充)。另外,在C语言中,结构体作为函数参数和返回值时,都是按值传递的。所以上面的函数返回的是整个结构体的副本。

还有一种情况,在函数定义时,如果结构体类型是在函数返回类型中定义的(即没有提前定义),那么需要先定义结构体类型,因为函数返回类型必须是一个完整的类型。

// 错误示例:不能在返回类型中直接定义结构体
struct Point create_point(int x, int y) { ... } // 如果Point未定义,则这样写是错误的
// 正确做法:先定义结构体类型,再使用
typedef struct Point Point;
struct Point {
    int x;
    int y;
};
Point create_point(int x, int y) { ... }

或者将结构体定义在函数返回类型之前:

// 正确示例:在函数返回类型之前定义结构体
struct Point {
    int x;
    int y;
};
struct Point create_point(int x, int y) {
    struct Point p = {x, y};
    return p;
}

如果使用typedef,则可以直接使用类型别名:

typedef struct {
    int x;
    int y;
} Point;
Point create_point(int x, int y) {
    Point p = {x, y};
    return p;
}

以下是完整代码示例

#include <stdio.h>

struct Point {
    int x;
    int y;
};

struct Point create_point(int x, int y);  


struct Point create_point(int x, int y) {
    struct Point p;
    p.x = x;
    p.y = y;
    return p; 
}


typedef struct {
    float width;
    float height;
} Rectangle;


Rectangle create_rectangle(float w, float h) {
    Rectangle rect = {w, h};
    return rect;
}

int main() {
   
    struct Point p1 = create_point(3, 4);
    printf("Point: (%d, %d)\n", p1.x, p1.y);
    

    struct Point p2 = create_point(10, 20);
    printf("Point: (%d, %d)\n", p2.x, p2.y);
    
    // 使用typedef定义的结构体
    Rectangle rect = create_rectangle(5.5, 3.2);
    printf("Rectangle: %.1f x %.1f\n", rect.width, rect.height);
    
    // 直接使用函数返回的结构体值
    printf("Area: %.2f\n", create_rectangle(2.0, 3.0).width * create_rectangle(2.0, 3.0).height);

    return 0;
}

结果

返回结构体 vs 返回结构体指针:

使用指针来传递结构体。

将结构体的指针作为函数参数传入(此时函数可以修改原结构体)

 1.定义一个结构体类型

#include <stdio.h>
#include <string.h>
struct Student {
    int id;
    char name[50];
    float score;
};

2.函数通过指针参数初始化结构体

void init_student(struct Student *stu, int id, const char *name, float score) {
    if (stu != NULL) { // 检查指针是否有效
        stu->id = id;
        strncpy(stu->name, name, sizeof(stu->name) - 1);
        stu->name[sizeof(stu->name) - 1] = '\0'; // 确保字符串结束
        stu->score = score;
    }
}

 3.另一个函数,用于打印学生信息,同样使用指针参数避免拷贝

void print_student(const struct Student *stu) {
    if (stu != NULL) {
        printf("Student ID: %d\n", stu->id);
        printf("Name: %s\n", stu->name);
        printf("Score: %.2f\n", stu->score);
    }
}

 4.通过指针参数更新结构体内容

void update_score(Student* stu, float new_score) {
    if (stu != NULL) {
        stu->score = new_score;
    }
}

 5.返回结构体指针的函数

Student* create_student(int id, const char* name, float score) {
    // 动态分配内存
    Student* new_stu = (Student*)malloc(sizeof(Student));
    if (new_stu != NULL) {
        new_stu->id = id;
        strncpy(new_stu->name, name, sizeof(new_stu->name) - 1);
        new_stu->name[sizeof(new_stu->name) - 1] = '\0';
        new_stu->score = score;
    }
    return new_stu; // 返回指针
}

6.返回静态结构体指针

Student* get_default_student() {
    static Student default_stu; // 静态存储期
    default_stu.id = 0;
    strcpy(default_stu.name, "Default");
    default_stu.score = 60.0f;
    return &default_stu; // 返回静态变量地址
}

主函数内,

int main() {

    // 方式1: 通过指针参数修改

    Student s1;
    init_student(&s1, 101, "Alice", 92.5f);
    printf("Student 1: %d, %s, %.1f\n", s1.id, s1.name, s1.score);

    update_score(&s1, 95.0f);
    printf("Updated Score: %.1f\n", s1.score);


    // 方式2: 返回动态分配的指针
 
    Student* s2 = create_student(102, "Bob", 85.5f);
    if (s2 != NULL) {
        printf("Student 2: %d, %s, %.1f\n", s2->id, s2->name, s2->score);

        // 修改动态分配的结构体
        update_score(s2, 88.0f);
        printf("Updated Score: %.1f\n", s2->score);

        free(s2); // 必须释放内存
    }


    // 方式3: 返回静态变量指针
  
    Student* s3 = get_default_student();
    printf("Default Student: %d, %s, %.1f\n", s3->id, s3->name, s3->score);

    // 修改静态结构体(影响所有调用者)
    s3->score = 65.0f;
    Student* s4 = get_default_student();
    printf("Modified Default: %.1f\n", s4->score); // 输出65.0

    return 0;
}
#include <stdio.h>
#include <stdlib.h>
#include <string.h>

// 1. 定义结构体类型
typedef struct {
    int id;
    char name[50];
    float score;
} Student;

// 2. 通过指针参数修改结构体
void init_student(Student *stu, int id, const char *name, float score) {
    if (stu != NULL) {
        stu->id = id;
        strncpy(stu->name, name, sizeof(stu->name) - 1);
        stu->name[sizeof(stu->name) - 1] = '\0'; // 确保字符串终止
        stu->score = score;
    }
}

// 3. 通过指针参数更新结构体内容
void update_score(Student *stu, float new_score) {
    if (stu != NULL) {
        stu->score = new_score;
    }
}

// 4. 返回结构体指针的函数
Student* create_student(int id, const char *name, float score) {
    // 动态分配内存
    Student *new_stu = (Student*)malloc(sizeof(Student));
    if (new_stu != NULL) {
        new_stu->id = id;
        strncpy(new_stu->name, name, sizeof(new_stu->name) - 1);
        new_stu->name[sizeof(new_stu->name) - 1] = '\0';
        new_stu->score = score;
    }
    return new_stu; // 返回指针
}

Student* get_default_student() {
    static Student default_stu; // 静态存储期
    default_stu.id = 0;
    strcpy(default_stu.name, "Default");
    default_stu.score = 60.0f;
    return &default_stu; // 返回静态变量地址
}

int main() {
    // ======================
    // 方式1: 通过指针参数修改
    // ======================
    Student s1;
    init_student(&s1, 101, "Alice", 92.5f);
    printf("Student 1: %d, %s, %.1f\n", s1.id, s1.name, s1.score);
    
    update_score(&s1, 95.0f);
    printf("Updated Score: %.1f\n", s1.score);
    
    // ======================
    // 方式2: 返回动态分配的指针
    // ======================
    Student *s2 = create_student(102, "Bob", 85.5f);
    if (s2 != NULL) {
        printf("Student 2: %d, %s, %.1f\n", s2->id, s2->name, s2->score);
        
        // 修改动态分配的结构体
        update_score(s2, 88.0f);
        printf("Updated Score: %.1f\n", s2->score);
        
        free(s2); // 必须释放内存
    }
    
    // ======================
    // 方式3: 返回静态变量指针
    // ======================
    Student *s3 = get_default_student();
    printf("Default Student: %d, %s, %.1f\n", s3->id, s3->name, s3->score);
    
    // 修改静态结构体(影响所有调用者)
    s3->score = 65.0f;
    Student *s4 = get_default_student();
    printf("Modified Default: %.1f\n", s4->score); // 输出65.0
    
    return 0;
}

结果