从 for while 开始的C语言学习(复习)之路 第一部分PART1

从 for while 开始的C语言学习(复习)之路PART 1 基础篇

PART 2 近期出解。/笑哭

总体来说 for 循环 和 while 循环 都是循环,可是就是些循环 却被我玩坏了。[玩坏过的勿喷]

第一个: for + scanf :

例如:    

for(int i;scanf("%d",&i),i;){ }
int i;
while(scanf("%d",&i),i){ }
while(scanf("%d",&i)!=EOF){ }
while(~scanf("%d",&i)) { }

一般会在各种书里会见到他们的影子。这里只是做出一点直观的解释。

1.它们都有一个共同的先决条件 -- 变量必须要先定义,然后才能使用。

for(int i;scanf("%d",&i),i;){ }

就像这个样例的for循环 在第一个;之前定义了一个变量,然后输入这个变量,判断这个变量是不是等于 0 ,如果等于 0 就会退出。 而有些新手可能就会写成下面这样,然后问为什么输入 0 后 循环不会退出??

for(int i;scanf("%d",&i);){ }

这就要讨论一下 scanf 它的返回值了 scanf到底是返回什么的 我们 可以使用 一个整型的变量来接收它看看。

int main(){

    int i,j;
    int c =scanf("%d%d",&i,&j);
    cout<<c;
    return 0;
}

当发生正常输入,那么输出结果是 2 。为什么呢?那是因为 scanf返回的是 你输入的元素个数 因为 scanf里面有两个%d 【什么,和你想的不一样,你是不是想因为有两个变量在scanf里 所以是 2??】那好,我们再做一个实验

int main(){

    int i,j;
    //int c =scanf("%d%d",&i,&j);
    int c =scanf("%d",&i,&j);

当发生正常输入的时候 输出 1. 然后我们接着做下面这个实验

                

int main(){

    int i,j;
    //int c =scanf("%d%d",&i,&j);
    int c =scanf("%d%d%d",&i,&j);
    cout<<c;
    return 0;
}

这回正常输入后  c 的值 是 3.  所以真正控制 scanf返回值的 我觉得应该是里边的%d . 

这就会让人想到一个符号 EOF 它的值是-1 它的用处是判断文件是不是输入结束。一般都是这两种写法

scanf("%d",&i)!=EOF
~scanf("%d",&i);

这两种写法,那么想玩的同学可能要问 这个要怎么才能使用啊!我好想让 scanf 返回值是-1啊! 在这里,因为笔者使用的是windows 系统 所以 仅仅介绍一下 windows 的操作。

在运行程序scanf等待用户输入的时候 按 ctrl + z 两个键,此时你会看见 程序框显示   ^z 这时按回车就会发现 scanf的返回值是-1了。

[又跑题了] 回归正题  for( 1 ; 2 ; 3)  1 只在循环一开始执行  2 只在下一循环开始之前执行  3 每次循环结束以后执行。为了方便理解 我写了三个程序。

    for(;int i=1;){
        scanf("%d",&i);
        cout<<" ";
        break;
    }
    for(int i;;){
        scanf("%d",&i);
        cout<<i<<" ";
        break;
    }

    // 以下编译错误
    for(;;int i=0){
        scanf("%d",&i);
        cout<<i<<" ";break;
    }
知道为什么会编译错误了吗?这就是我之前提到的 for( 1 ; 2 ; 3)  1 只在循环一开始执行  2 只在下一循环开始之前执行  3 每次循环结束以后执行。所以 定义在 使用的后面 所以编译出错。而第一段代码必须给i赋初值,否则同样编译不通过,原因应该是中间那个是判断循环是否继续执行的条件,所以只接受 0 和 非0 这种数据吧!  (bool值也可以使用 %d 的方法进行输出,也会发现是 0 和 1.)


所以 我有一种奇怪的写法 来看一看

   while(int i=1){
        scanf("%d",&i);
   }

这样的写法正是等同于 for(;int i;){} 这种写法。 所以 我们得出了一个什么样子的结论呢??

任意的while()可以使用for() 进行替换。那 while(scanf("%d",&i)!=EOF) 这个能不能进行替换呢?? 试一下就知道了

   for(int i;scanf("%d",&i)!=EOF;){
        ;
   }

或者是这样

   for(int i;~scanf("%d",&i);){
        ;
   }

我发现 这两条也是可以通过编译器进行编译的。所以可以暂说for 可以 替代 while . 

那它们之间 到底是谁效率高呢???

网上都有讨论 据说 九十年代有过测试 证明过 while 的效率优于 for 不过 更多的,我们现在的计算机配置,似乎已经看不到差别了吧!!!


所以 那么冒泡排序的 while 的写法 是不是 可以试试看呢~~~  我们要善于观察 for 和 while 的 差异性

这个是用 for 写的 冒泡排序

int main(){

    int a[10]={1,3,2,5,4,7,6,9,8,0};
    for(int i=1;i<10;i++)
        for(int j=0;j<10-i;j++)
            if(a[j]>a[j+1])
                swap(a[j],a[j+1]);
    for(int i=0;i<10;i++)
        cout<<a[i]<<" ";
}

这个是用 while 写的 冒泡排序

int main(){

    int a[10]={1,3,2,5,4,7,6,9,8,0};
    int i=1,j;
    while(i<10){
        j = 0;
        while(j<10-i){
            if(a[j]>a[j+1])
                swap(a[j],a[j+1]);
            j++;
        }
        i++;
    }
    for(int i=0;i<10;i++)
        cout<<a[i]<<" ";
}

就发现了for 和 while 的 残留问题  for 循环 可以轻松定义局部的变量 避免了 空间的浪费 而while 循环却会残余变量,那是不是就无解了呢?? 不是的 !! 还记得  { } 花括号的用法吗??我们把 排序所需要的代码用 花括号括起来 

int main(){

    int a[10]={1,3,2,5,4,7,6,9,8,0};
{  // 我是一个可爱的花括号

    int i=1,j;
    while(i<10){
        j = 0;
        while(j<10-i){
            if(a[j]>a[j+1])
                swap(a[j],a[j+1]);
            j++;
        }
        i++;
    }
} // 我也是一个可爱的花括号,你看见我了吗== 喂
  //  cout<<i<<endl; // 你们猜 这条语句 可以编译的过去吗?? 答案:是不能编译过去的。所以局部变量的概念掌握了吗??
    for(int i=0;i<10;i++)
        cout<<a[i]<<" ";
}

所以 并不是像我之前所说的那样 会有这种 多余的 东西存在。所以仁者见仁,智者见智,使用方略其实是非常宽广的嘛!!

根据我们的学习我们会发现 其实并不像老师所说 for 循环是有循环次数才使用,while是未知循环次数才使用的。

下面讲一下  循环 for 的指针和字符串的 使用方法。

再讲这个之前 我们讲一下 指针的 使用方法。

指针 分为 很多种 什么 int* char* string* (c++) 迭代器指针啊等等等。 第一节课的时候老师说 指针保存的是指向元素的地址。随着学习的逐渐深入 发现 并不是完全是这样的。为什么呢??我们举一个例子 

    char i = 'c';
    int t = (int)i;

这种写法大家都是认为可以这样的吧!!因此无论怎么变 指针变量 可以理解是一种指向它本身基类型的类型,总之就是类型,是类型就可以用强制类型转换进行赋值。因此我们不难说明以下代码是正确的

int* i = (int*)1;

接着我们 还知道了 已知数组中间元素的地址 ,那么用它来减去首地址就会得出这个元素在数组的位置。这个就说明了指针可以进行加减运算 ,然后我们可以猜想它能不能进行乘除运算呢?好!上代码

    int* i = (int*)1;
    int* j = (int*)2;
    cout<<i*j<<endl; // 我是错误的代码 你发现我了吗??

所以是不能进行乘除运算的!!!!

那么指针是 怎么进行加减运算的呢??它又拿什么进行运算的呢??例如: j - i

    int* i = (int*)1;
    int* j = (int*)2;
    cout<<j - i<<endl;

答案是多少呢??反正不是 1 而是 0 !!!!为什么是 0 呢?因为 int 类型是 占用 4 个字节的空间 即 [1,4] 闭区间哦!!

所以两个相同类型的指针相减 减得是 所占用的那个空间 1 和 2 都是第一个空间 所以 1-1==0 正确!

我们又来看下下面这个程序

int main(){

    int* p =NULL;
    int k = (int)p;
    cout<<k;
}

k的值是多少 ?答案是 0 。说明了什么 int* p =NULL 就等价于 int *p = (int *)0; 呀!!不信?

我们看看下面这个程序

    int* p =NULL;
    int* k = (int *)0;

    if(p == k)
        cout<<"我对了"; // 是输出的我 看见我了吗??喂!
    else
        cout<<"继续努力";

我们还知道 '\0'代表的是 0 那么我们可以演示一下这个程序:  (逐渐进入今天的正题

    char* p =NULL;

    if(p == '\0') // 或者 if(p == 0)
        cout<<"我对了"; // 是我是我!!
    else
        cout<<"继续努力"; // ………………

现在 我们 看 正题 ,哎对了 正题是什么来着??

循环 for 的指针和字符串的 使用方法。(肯定我掌握的不如那些牛叉的大佬了,所以想要学更多的东西还得靠手 不是靠喷!)

我们都知道 字符串 是由若干个字符在和'\0'在一段连续的空间中组成的。间断的空间是无法构建字符串的。比如用链表来存。

我们来看下面一个代码:

 char *s = "nihao ma";

现在问一下 一共有多少个有效字符 一共有8 个有效字符。

再问一下 一共有多少个字符 因为是直接赋值 所以我们有三种方法 知道这个结果:

1. 使用strlen函数的返回值+1  即 int i = sizeof(s);  返回值是 9、

2.一眼看出来,你不会不懂数数吧??/笑哭

3.因为这个是一个直接赋值的字符串 所以 可以直接调用 sizeof() 来查 ,所以 int i = sizeof(s); 返回值是 9

但是注意 sizeof 用于查看这个数组剩余的空间的 我们再扯一下 sizeof()这个函数:

char a[6];
cout<<sizeof(p);

那都不用想啊 肯定返回的是 6 啊??为什么??因为char 类型一个占用1 个空间 一共有 6 个 因此 1*6 == 6 就是这么来的。

那也就是可以拓展为

int a[6];
cout<<sizeof(p);

返回的是 4*6 == 24  答案正确

那 给定一个字符串 我们怎样遍历呢??

是这样??

for(int i=0,j=strlen(str);i<j;i++)

;

还是这样??

for(int i=0;str[i]!='\0';i++)

;

还是 一种特殊的方法

for(char* s=str;*s!='\0';s++)

;

推荐使用第三种 方法 只是推荐  ,那有人会问我怎么知道我正在处理的元素是第几个元素呢??其实这个非常好处理,只需要

当前指针 - 数组的首部指针 。无论是 malloc定义的 还是 int 直接定义的  都可以通过减法计算出当前处理的元素的位置。

即 s - str == 当前元素的个数。

下回再见。哈哈哈 别怪我下回放难的呀??基础不牢地动山摇./笑哭

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
在现有省、市港口信息化系统进行有效整合基础上,借鉴新 一代的感知-传输-应用技术体系,实现对码头、船舶、货物、重 大危险源、危险货物装卸过程、航管航运等管理要素的全面感知、 有效传输和按需定制服务,为行政管理人员和相关单位及人员提 供高效的管理辅助,并为公众提供便捷、实时的水运信息服务。 建立信息整合、交换和共享机制,建立健全信息化管理支撑 体系,以及相关标准规范和安全保障体系;按照“绿色循环低碳” 交通的要求,搭建高效、弹性、高可扩展性的基于虚拟技术的信 息基础设施,支撑信息平台低成本运行,实现电子政务建设和服务模式的转变。 实现以感知港口、感知船舶、感知货物为手段,以港航智能 分析、科学决策、高效服务为目的和核心理念,构建“智慧港口”的发展体系。 结合“智慧港口”相关业务工作特点及信息化现状的实际情况,本项目具体建设目标为: 一张图(即GIS 地理信息服务平台) 在建设岸线、港口、港区、码头、泊位等港口主要基础资源图层上,建设GIS 地理信息服务平台,在此基础上依次接入和叠加规划建设、经营、安全、航管等相关业务应用专题数据,并叠 加动态数据,如 AIS/GPS/移动平台数据,逐步建成航运管理处 "一张图"。系统支持扩展框架,方便未来更多应用资源的逐步整合。 现场执法监管系统 基于港口(航管)执法基地建设规划,依托统一的执法区域 管理和数字化监控平台,通过加强对辖区内的监控,结合移动平 台,形成完整的多维路径和信息追踪,真正做到问题能发现、事态能控制、突发问题能解决。 运行监测和辅助决策系统 对区域港口与航运业务日常所需填报及监测的数据经过科 学归纳及分析,采用统一平台,消除重复的填报数据,进行企业 输入和自动录入,并进行系统智能判断,避免填入错误的数据, 输入的数据经过智能组合,自动生成各业务部门所需的数据报 表,包括字段、格式,都可以根据需要进行定制,同时满足扩展 性需要,当有新的业务监测数据表需要产生时,系统将分析新的 需求,将所需字段融合进入日常监测和决策辅助平台的统一平台中,并生成新的所需业务数据监测及决策表。 综合指挥调度系统 建设以港航应急指挥中心为枢纽,以各级管理部门和经营港 口企业为节点,快速调度、信息共享的通信网络,满足应急处置中所需要的信息采集、指挥调度和过程监控等通信保障任务。 设计思路 根据项目的建设目标和“智慧港口”信息化平台的总体框架、 设计思路、建设内容及保障措施,围绕业务协同、信息共享,充 分考虑各航运(港政)管理处内部管理的需求,平台采用“全面 整合、重点补充、突出共享、逐步完善”策略,加强重点区域或 运输通道交通基础设施、运载装备、运行环境的监测监控,完善 运行协调、应急处置通信手段,促进跨区域、跨部门信息共享和业务协同。 以“统筹协调、综合监管”为目标,以提供综合、动态、实 时、准确、实用的安全畅通和应急数据共享为核心,围绕“保畅通、抓安全、促应急"等实际需求来建设智慧港口信息化平台。 系统充分整合和利用航运管理处现有相关信息资源,以地理 信息技术、网络视频技术、互联网技术、移动通信技术、云计算 技术为支撑,结合航运管理处专网与行业数据交换平台,构建航 运管理处与各部门之间智慧、畅通、安全、高效、绿色低碳的智 慧港口信息化平台。 系统充分考虑航运管理处安全法规及安全职责今后的变化 与发展趋势,应用目前主流的、成熟的应用技术,内联外引,优势互补,使系统建设具备良好的开放性、扩展性、可维护性。
提供的源码资源涵盖了安卓应用、小程序、Python应用和Java应用等多个领域,每个领域都包含了丰富的实例和项目。这些源码都是基于各自平台的最新技术和标准编写,确保了在对应环境下能够无缝运行。同时,源码中配备了详细的注释和文档,帮助用户快速理解代码结构和实现逻辑。 适用人群: 这些源码资源特别适合大学生群体。无论你是计算机相关专业的学生,还是对其他领域编程感兴趣的学生,这些资源都能为你提供宝贵的学习和实践机会。通过学习和运行这些源码,你可以掌握各平台开发的基础知识,提升编程能力和项目实战经验。 使用场景及目标: 在学习阶段,你可以利用这些源码资源进行课程实践、课外项目或毕业设计。通过分析和运行源码,你将深入了解各平台开发的技术细节和最佳实践,逐步培养起自己的项目开发和问题解决能力。此外,在求职或创业过程中,具备跨平台开发能力的大学生将更具竞争力。 其他说明: 为了确保源码资源的可运行性和易用性,特别注意了以下几点:首先,每份源码都提供了详细的运行环境和依赖说明,确保用户能够轻松搭建起开发环境;其次,源码中的注释和文档都非常完善,方便用户快速上手和理解代码;最后,我会定期更新这些源码资源,以适应各平台技术的最新发展和市场需求。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值