for循环的实例分析

for循环嵌套

  • for(定义或初始化; 条件表达式; 调整表达式){}
  • while和if的结合体: 循环判断执行循环体; 有些语言还可以配合to语句

三个表达式可以按需要省略, ;却不能省略。for( ; ; ) == while(1/True); --程序可读性

///: C:for循环嵌套
// 分析内部作为整体再外部循环,分步乘法
// 执行顺序为:一层外部整体的内部到二层外部整体
#include <stdio.h>

int main() {
    int i,j;

    for(i=0; i<10; i++) {
        for(j=0; j<10; j++) {
            printf("i= %d, j= %d\n", i, j); // 10*10 次循环
        }
    }
}

for循环条件调整表达式

///: C:for循环条件调整表达式
// 将for作为if-while循环分析
#include <stdio.h>

int main() {
    int i;

    for(i=1; i<100; i++) {
        // Equivalent: int=1;while(i<100) {i++;}
        break; //Not-break; i= 100;
    }
    printf("i= %d\n", i); //i= 1 需要使用break; 因为for语句块可以访问到外部定义
}

for循环实时变量

///: C:for循环实时变量
// 实时变量;在需要的地方定义的变量, 自动(屏蔽)存储期
// 允许定义和初始化-std=C99, -std=gnu99, 作为实时变量调整作用域只在for程序块
#include <stdio.h>

int main() {
    int i=520; // 外部定义
    for(int i=0, j=10; i<j; i++,j--) {
        printf("%d\n", i);
    }
    // 局部实时变量不会影响到外部定义
    printf("%d\n", i);
}

gcc -std=c99 C\for实时变量.c

for循环与while的差异

///: C:for循环与while的差异
// 计数器在for语句对比while优先级大
#include <stdio.h>

int main() {
    int i;

    i=0;
    while(i<100) {
        if(i % 2) {
            continue;
        }  
        i++; // 在continue下计数器并不会执行
    }
    // for(i=0; i<100; i++) {
    //     if(i % 2) {
    //         continue;
    //     }
    // }

    return 0;
}

for循环遍历接收数组

///: C:for遍历/接收数组
// i=0; 下阶不越界。 i+1, 定义数对应下阶
#include <stdio.h>

#define NUM 10

int main() {
    int s[NUM];
    int i, sum=0;

        for(i=0; i<10; i++) {
            printf("请输入第%i位同学的成绩: ", i+1);
            scanf("%d", &s[i]);
            sum += s[i];
        }

        printf("成绩录入完成, 该次考试的平均分是: %2.f\n", (double)sum / NUM);

    return 0;
}

for循环遍历二维数组

///: C:for遍历二维数组
// 内部可以访问到外部实时变量
#include <stdio.h>

int main() {
    int a[3][4]={
                     {1,2,3,4},
                     {5,6,7,8},
                     {9,10,11,12}
    }; 

    for(int i=0; i<3; i++) {
        for(int j=0; j<4; j++) {
            printf("%d \n",a[i][j]);
        }
    }
}

for循环遍历指针数组

///: C:for遍历指针数组
#include <stdio.h>

int main() {
    // int a=1;
    // int b=2;
    // int c=3;
    // int d=4;
    // int e=5;
    // int *p1[5] = {&a,&b,&c,&d,&e};
    // printf("%d", *p1[i]);  // 遍历指针数组的指针数组
// char类型指针,约定引用时只需传递字符串起始地址, 只需知道第一个字符从而得到整个字符串
    char *p1[5] = {
        "让程序改变世界",
        "Just do it",
        "一切皆有可能",
        "永不止步",
        "One more thing"
    };
    
    for(int i=0; i<5; i++) {

// %s的工作方式是,它期望一个指向字符数组(字符串)首字符的指针,指数法直到遇到字符串结束符'\0'。
// 对于指针数组, p1[i] 等价于 *(p+i) 指针法, 此时p数组等价于数组名
        printf("address= %s\n", p1[i]); // p1[0] 等价于 字符“让”的指针
    }

    return 0;
}

for循环遍历数组指针

///: C:for遍历数组指针
#include <stdio.h>

int main() {

    int temp[5] = {1,2,3,4,5};

    // 先让*p2指向包含所有元素数组的指针
    int (*p2)[5] = &temp;


    for(int i=0; i<5; i++) {
// p2指向包含所有元素数组的指针,所以*p2指针是数组本身,又因为数组(本身)是指向首元素的地址,所以*(*p2+i)引用到了指针法的元素
        printf("%d\n", *(*p2+i));
    }

    return 0;
}

for循环遍历二维数组的指针

///: C:for循环遍历二维数组的指针
#include <stdio.h>

int main() {
    int array[4][5] = {0};
    int i,j,k = 0;

    for(i=0; i<4; i++) {
        for(j=0; j<5; j++) {
            array[i][j] = k++;
        }
    }

    printf("array: %p\n", array);
    printf("array: %p\n", *array);       // 逐底层访问: array等价于*array等价于&array[0][0]
// *array访问到一维数组本身,又因为一维数组(本身)是指向首元素的地址, **array才能访问到元素
    printf("array: %d\n", **array);
    printf("*(array+1): %p\n", *(array + 1));
    printf("array[1]: %p\n", array[1]);
    printf("&array[1][0]: %p\n", &array[1][0]);
    printf("**(array+1): %d\n", **(array+1));
    printf("**(array+1)+3: %d\n", **(array+1)+3);
    printf("array[1][3]: %d\n", array[1][3]);
    

    return 0;
}

for循环遍历指向指针数组的指针数组

///: C:for循环遍历指向指针数组的指针数组
// p外层地址 , *p内层地址, **p解运算元素
// 自己作为外层地址可引用到内层地址
#include <stdio.h>

int main() {
    char *cBook[]   = {
        "{C程序设计语言}",
        "{C专家code}",
        "{C和指针}",
        "{C的陷阱与缺陷}",
        "{C primer plus}",
        "{ccode思想}",
    };

    char **byFishC;
// 存放四个地址元素的嵌套指针
    char **jiayuLoves[4];

// 内层地址引入到本身外层地址
    byFishC = &cBook[5];
    jiayuLoves[0] = &cBook[0]; 
    jiayuLoves[1] = &cBook[1]; 
    jiayuLoves[2] = &cBook[2]; 
    jiayuLoves[3] = &cBook[3]; 

// *byFishC直接引用内层地址地址
    printf("Fishc: %s\n", *byFishC);
    printf("喜欢的图书有: \n");
    for(int i=0; i<4; i++) {
// *jiayuLoves内层地址地址
        printf("%s\n", *jiayuLoves[i]);
    }

    return 0;
}

for循环通过二维数组指针遍历二维数组

///: C:for循环通过二维数组指针遍历二维数组
// 无法通过耽搁嵌套指针引用二维数组
#include <stdio.h>

int main() {
    int array[4][5] = {0};
    // int **p = array;
    int (*p)[4][5] = &array;
    int i,j,k = 0;

    for(i=0; i<4; i++) {
        for(j=0; j<5; j++) {
            printf("%2d ", ***((p+i)+j));
        }
    }

    

    return 0;
}

for循环遍历函数传入的数组

///: C:for循环遍历函数传入的数组

#include <stdio.h>

void get_array(int a[10]) {
    int i;

    a[5] = 520;

    for(i=0; i<10; i++) {
        printf("a[%d]= %d\n", i, a[i]);
    }
}

int main() {
    int a[10] = {1,2,3,4,5,6,7,8,9};

// get_array(&a) 无法像指针数组一般将数组作为整体传入
// 传入的是a数组的首元素指针
    get_array(a);

    int i;
    printf("main函数里面再打印一次:...\n");
    for(i=0; i<10; i++) {
        printf("a[%d]= %d\n", i, a[i]);
    }

    return 0;
}

for循环遍历函数静态变量

///: C:for循环遍历静态(局部)变量
#include <stdio.h>

void func(void) {

// 只会初始化一次,保留上次初始化后的内存 --静态存储期
    static int count=0;

    printf("count = %d\n", count);
    count++;
}

int main(void) {
    int i;
    for(i=0; i<10; i++) {
        func();
    }
}

for循环实现阶乘运算

///: C:for循环实现阶乘计算
// 阶乘公式推导: m!=1*2*3*(m-1)*m
// 递归公式推导: m!=m*(m-1)!

#include <stdio.h>
int result=1;

int main() {
    for(int i=10; i>1; i--) {
        result *= i;
    }

    printf("10的阶乘是: %d\n", result);
}

for循环遍历分配空间的数组指针

#include <stdio.h>
#include <stdlib.h>

int main(void) {
    int i,num;
    int count = 0;
    int *ptr = NULL;

    do {
        printf("请输入一个整数(输入-1表示结束):");
        scanf("%d", &num);
        count++;

  // 此时ptr作为数组指针, 并分配了内存空间
        ptr = (int *)realloc(ptr, count * sizeof(int));
        if(ptr == NULL) {
            exit(1);
        }

        ptr[count-1] = num; //   // 动态
    } while(num != -1);

    printf("输入的整数分别是:");
    for(i=0; i< count; i++) {
        printf("%d", ptr[i]); // 遍历数组指针, ptr[i] 等价于 *(ptr+i)  不等价于ptr相当于数组名
    }
    putchar('\n');
    
    // 释放内存
    free(ptr);

    return 0;
}

for循环打印枚举类型

/// C:for循环打印枚举类型
// 本质是整型常量的集合, 从0开始默认赋值枚举常量
#include <stdio.h>

int main(void) {

    enum Color {red=10, green, blue};
    enum Color rgb;

    // 由于枚举类型是连续的,用for遍历
    for(rgb=red; rgb<= blue; rgb++) {
        printf("rgb is %d \n", rgb);
    }

}

for循环遍历结构化数组

///: C:for循环遍历结构化数组
#include <stdio.h>
#include <stdlib.h>

#define N 4

struct Stu {
    char name[24];
    int num;
    float score;
} stu[N], sb; // 实例化结构体数组

int main(void) {
    FILE *fp;
    int ch;
    char filename[51] = "/Users/nagisb/Documents/C-Project/custom/hello.txt";

    if((fp=fopen(filename,"wb")) == NULL) {
        printf("文件打开失败!\n");
        exit(EXIT_FAILURE);
    }

    printf("请开始录入成绩(格式:姓名 学号 成绩)");
    for(int i=0; i<N; i++) {
        scanf("%s %d %f", stu[i].name, &stu[i].num, &stu[i].score);
    }

    fwrite(stu, sizeof(struct Stu), N, fp);
    fclose(fp);

    if((fp=fopen(filename,"rb")) == NULL) {
        printf("文件打开失败!\n");
        exit(EXIT_FAILURE);
    }

    fseek(fp, sizeof(struct Stu), SEEK_SET);
    fread(&sb, sizeof(struct Stu), 1, fp);
    printf("%s(%d)的成绩是:%.2f\n", sb.name, sb.num, sb.score);
    fclose(fp);

    return 0;
}
posted @ 2024-11-01 16:01  NAGISB  阅读(4)  评论(0编辑  收藏  举报