C语言基础三

1、截取指定字符串

#include 
#include 
#include 

//第一种
void substrAction1(char *result, char *str, int start, int end) {
    char *temp = str; //定义临时指针,不破坏str
    int count = 0;
    while (*temp) {
        if (count >= start && count < end) {
            *result = *temp;  //边移动指针边接收值
            result++;
        }
        temp++;
        count++;
    }
}

//第二种 理解栈区 堆区分配
void substrAction2(char **result, char *str, int start, int end) {
    char *temp = str;
    //合理分配,用多少分配多少
    char resultArr[end - start];

    int count = 0;
    for (int i = start; i < end; ++i) {
        resultArr[count] = *(temp + i);
        count++;
    }

//    *result = resultArr; //不能让一级指针指向容器,函数执行结束后会回收容器,main函数里result会为空
    //指向容器问题解决1:使用copy
    strcpy(*result, resultArr);


    //指向容器问题解决2:动态分配内存
//    char * resultArr = malloc(end-start);
//    int count = 0;
//    for (int i = start; i < end; ++i) {
//        resultArr[count] = *(temp + i);
//        count++;
//    }
//    *result = resultArr; //不能让一级指针指向容器,函数执行结束后会回收容器,main函数里result会为空

    //但是使用第二种要手动释放,但是已释放,main函数里还是为空,所以要在main函数释放,
    // 但是这种做法不好,如果提供给别人使用,你还要别人去释放,所以推荐第一种
    //free(resultArr);
    printf("%s\n", resultArr);
}

//第三中
void substrAction3(char *result, char *str, int start, int end) {
    for (int i = start; i < end; ++i) {
        *(result++) = *(str + i);
    }
}
//第三中
void substrAction4(char *result, char *str, int start, int end) {
    strncpy(result,str+start,end-start);
}

int main() {

    char *str = "HelloWorld";
    char *result;
    //substrAction1(result, str, 2, 5);

    //substrAction2(&result, str, 2, 5);

    //解决指向容器问题的,第二种方法的释放
//    if (result){
//        free(result);
//        result = NULL;
//    }

    //substrAction3(result, str, 2, 5);
    substrAction4(result, str, 2, 5);
    printf("截取的内容:%s", result);
    return 0;
}

一、结构体

1、几种写法

//第一种写法
#include 
#include 
#include 
#include 
struct Dog {
    // 成员
    char name[10]; // copy进去
    int age;
    char sex;
}; // 必须给写;
int main() {
    struct Dog dog; // 这样写完,成员是没有任何初始化的,成员默认值 是系统值(name:?@, age:3133440, sex:)
    printf("name:%s, age:%d, sex:%c \n", dog.name, dog.age, dog.sex);

    // 赋值操作
    // dog.name = "旺财";
    strcpy(dog.name, "旺财");
    dog.age = 3;
    dog.sex = 'G';
    printf("name:%s, age:%d, sex:%c \n", dog.name, dog.age, dog.sex);
    return 0;
}
//第二种写法
#include 
#include 
#include 
#include 
struct Person {
    // 成员
    char * name; // 字符指针 = "赋值"
    int age;
    char sex;
} ppp = {"Derry", 33, 'M'},
ppp2,
ppp3,
pppp4,
pppp5
// ...
;
int main() {
    // Person == ppp == struct Person ppp;
    printf("name:%s, age:%d, sex:%c \n", ppp.name, ppp.age, ppp.sex);
    // 赋值
    // strcpy(pppp5.name, "Derry5"); // Copy不进去
    pppp5.name = "DerryO";
    pppp5.age = 4;
    pppp5.sex = 'M';
    printf("name:%s, age:%d, sex:%c \n", pppp5.name, pppp5.age, pppp5.sex);
    return 0;
}
//第三种
#include 
#include 
#include 
#include 
struct Study {
    char * studyContent; // 学习的内容
};
struct Student {
    char name[10];
    int age;
    char sex;
    // Study study; // VS的写法
    struct Study study; // Clion工具的写法
    struct Wan {
        char * wanContent; // 玩的内容
    } wan;
};
int main() {
   struct Student student =
            {"李元霸", 88, 'm' ,
             {"学习C"},
             {"王者农药"}
             };
    printf("name:%s, age:%d, sex:%c,study:%s, wan:%s \n",
           student.name, student.age, student.sex, student.study.studyContent, student.wan.wanContent);
    return 0;
}

二、结构体指针

//栈区
#include 
#include 

struct Cat {
    char name[10];
    int age;
};
int main() { // 栈
    // 结构体
    struct Cat cat = {"小花猫", 2};

    // 结构体 指针    -> 调用一级指针成员
    // VS的写法:Cat * catp = &cat;
    struct Cat * catp = &cat;
    catp->age = 3;
    strcpy(catp->name, "小花猫2");
    printf("name:%s, age:%d \n", catp->name, catp->age);
    return 0;
}
//堆区
#include 
#include 
#include 
struct Cat2 {
    char name[10];
    int age;
};
int main() { // 堆
    // VS的写法:Cat2 * cat = (Cat2 *) malloc(sizeof(Cat2));
    struct Cat2 *cat = malloc(sizeof(struct Cat2));
    strcpy(cat->name, "金色猫");
    cat->age = 5;
    printf("name:%s, age:%d \n", cat->name, cat->age);
    // 堆区的必须释放
    free(cat);
    cat = NULL;
    return 0;
}

三、结构体数组

#include 
#include 
#include 

struct Cat {
    char name[10];
    int age;
};

int main() {
    //静态栈区
    struct Cat cat[5] = {
            {"小白", 3},
            {"小黑", 4},
            {"小黄", 5},
            {},
            {}
    };
    //VS写法
    //cat[4] = {'小红',6};

    //Clion
    struct Cat cat1 = {"小红", 6};
    //cat[4] = cat1;
    *(cat + 4) = cat1;

    for (int i = 0; i < 5; ++i) {
        printf("%s的年龄是%d\n", cat[i].name, cat[i].age);
    }

    //动态堆区
    struct Cat *cat2 = malloc(sizeof(struct Cat) * 5);
    //赋值
    strcpy(cat2->name, "小狼"); //首地址第一个元素
    cat2->age = 6;
    printf("name:%s,age:%d\n", cat2->name, cat2->age);

    //给第三个赋值
    cat2 += 2;
    strcpy(cat2->name,"小虎");
    cat2->age = 7;
    printf("name:%s,age:%d", cat2->name, cat2->age);

    free(cat2);
    cat2 = NULL;
    return 0;
}

四、别名

#include 
#include 

struct DAO {
    char name[10];
    int age;
    char sex;
};

// 匿名结构体的别名(这样写意义不大,因为没有名字)
typedef struct {
    char name[10];
    int age;
    char sex;
};

// 源码是这样写的
// 给结构体 取了一个别名Person
typedef struct {
    char name[10];
    int age;
    char sex;
} Person;

// 取一个别名
typedef struct DAO DAO;

void show(DAO dao) {} // 在不同工具上 又的要加,又的不用加 又差异化

int main() {
    // VS 不需要这样写,   Clion工具 要加入关键字  代码不统一
    // struct DAO * dao  = malloc( sizeof(struct DAO));

    // 加别名后  代码的统一了
    DAO * dao  = malloc( sizeof(DAO));

    // 加别名后  代码的统一了
    // C库的源码,系统源码...,为什么 typedef 还取一个和结构体一样的名字(兼容代码的写法,保持一致)
    Person p= {"lisi", 54, 'M'}; // 结构体  VS  Clion  xxx工具  兼容写法
    Person * p = malloc(sizeof(Person)); // 结构体指针
    return 0;
}

五、枚举

#include 
// 枚举 int 类型的
enum CommentType {
    TEXT = 10,
    TEXT_IMAGE,
    IMAGE
};
typedef enum CommentType CommentType;
int main() {
    // Clion工具的写法如下:
   // enum CommentType commentType = TEXT;
    //enum CommentType commentType1 = TEXT_IMAGE;
   // enum CommentType commentType2 = IMAGE;

    // VS工具的写法如下:
    // CommentType commentType = TEXT;

  //取别名后
  // CommentType commentType = TEXT;
    printf("%d, %d, %d \n", commentType, commentType1, commentType2);
    return 0;
}

你可能感兴趣的:(C语言基础三)