C语言星号的秘密
c语言运算符
c语⾔运算符1.运算符概述运算符是⼀种编译器执⾏特定的数学或逻辑操作的符号。
C语⾔提供了以下类型的运算符:算术运算符关系运算符逻辑运算符位运算符赋值运算符条件运算符其他运算符2.算术运算符算术运算符分为单⽬运算符和双⽬运算符,单⽬运算符表⽰只需要⼀个操作数,双⽬运算符需要两个操作数。
# 2.1 双⽬算术运算符1)+ :加法,把两个操作数相加2)- :减法,从第⼀个操作数中减去第⼆个操作数3)* :乘法,把两个操作数相乘4)/ :除法,第⼀个操作数除以第⼆个操作数5)% :求模(取余),第⼀个操作数除以第⼆个操作数所得余数双⽬运算符中,C语⾔中的加号、减号与数学中的⼀样。
乘号、除号因为ASCII符号中没有与数学中相对应的符号,所以使⽤星号表⽰乘号,使⽤斜线表⽰除号。
C语⾔中增加了⼀个求模运算符,是⽤来取余的。
需要注意的是,求模运算符的两个操作数必须是整型。
【实例6.1】加减乘除以及取模运算#include <stdio.h>int main(){int a = 21;int b = 10;int c;float d = 2.5;double e;int f = -21;int g = -10;c = a + b;printf(" a + b = %d\n", c);c = a - b;printf(" a - b = %d\n", c);c = a * b;printf(" a * b = %d\n", c);c = a / b;printf(" a / b = %d\n", c);e = a / d;printf(" a / d = %lf\n", e);c = a % b;printf(" a %% b = %d\n", c);c = a % g;printf(" a %% g = %d\n", c);c = f % b;printf(" f %% b = %d\n", c);c = f % g;printf(" f %% g = %d\n", c);return0;}执⾏以上程序,输出结果为:a +b = 31a -b = 11a *b = 210a /b = 2a / d = 8.400000a %b = 1a % g = 1f % b = -1f %g = -1实例解析:加、减与数学中的⼀样,其中需要说明的是除法以及取模运算。
c的小符号
c的小符号C语言是一种广泛使用的编程语言,它使用了许多特殊的符号来表示不同的意义和功能。
下面是一些常见的C语言符号及其用途的介绍。
1. 分号 (;):在C语言中,分号是语句结束符号。
每条语句必须以分号结束,以指示编译器这是一个完整的语句。
2. 大括号 ({}):大括号用于表示代码块,也称为作用域。
在C语言中,大括号用于定义函数、循环和条件语句的主体。
所有位于一对大括号之间的代码将被视为一个独立的代码块。
3. 小括号 (()):小括号在C语言中用于不同的目的。
最常见的用途是调用函数时传递参数。
小括号也可以用于数学表达式中来改变运算优先级。
4. 方括号 ([]):C语言中的方括号用于创建和访问数组。
通过在方括号内指定索引,可以访问数组中的特定元素。
方括号也可以用于定义全局数组或指定数组的大小。
5. 引号 ('' 或 ""):引号在C语言中用于表示字符或字符串。
单引号用于表示单个字符,例如 'A',而双引号用于表示字符串,例如 "Hello, World!"。
6. 星号 (*):星号在C语言中有多种用途。
最常见的用途是表示指针类型。
在变量前加上星号可以声明一个指针变量。
星号还可以用于乘法运算符。
7. 运算符 (+, -, *, /, %):C语言中有许多运算符用于执行不同类型的操作。
加号用于加法,减号用于减法,星号用于乘法,斜杠用于除法,百分号用于取模运算。
8. 等号 (=):等号是赋值运算符,在C语言中用于给变量赋值。
通过将右侧的值赋给左侧的变量,可以在程序中存储和操作数据。
这些只是C语言中一些常见的小符号,而实际上C语言具有更多其他符号用于各种编程任务。
通过熟悉和理解这些符号的用途,开发者可以编写出高效、功能强大的C程序。
用c语言编写 星号树状结构的程序
用c语言编写星号树状结构的程序C语言是一门非常重要的编程语言,具有广泛的应用领域。
为了帮助大家更好地理解和运用C语言,本文将编写一个用C语言实现星号树状结构的程序。
首先,我们需要了解一下星号树状结构的概念。
星号树状结构是一种以星号符号(*)组成的图形,呈现出树的形状。
它由单个星号组成的树干和逐渐增多的星号组成的树枝构成。
通过控制星号的数量和分布,我们可以创建出各种形态各异的树状结构。
接下来,我们开始编写程序。
首先,我们需要使用C语言的循环结构来控制星号的数量和分布。
我们定义一个变量n,表示树枝的层数。
然后,使用for循环控制树枝的层数,每次循环打印出对应层数的星号数量。
具体步骤如下:1. 首先定义一个整型变量n,表示树枝的层数。
可以让用户输入一个整数作为树枝的层数,以增加程序的交互性。
2. 使用for循环结构控制树枝的层数。
for循环的控制变量i从1递增到n,每次循环打印一行星号。
3. 在每次循环中,使用另一个for循环控制星号的数量。
控制变量j从1递增到i,每次循环打印一个星号。
4. 打印完一行星号后,使用printf函数打印一个换行符,以换行并将下一行的星号与上一行的星号分隔开。
5. 循环结束后,整个星号树状结构将打印完毕。
通过以上步骤,我们成功地编写了一个用C语言实现星号树状结构的程序。
这个程序不仅可以生成各种形态的星号树状结构,还可以通过用户输入的层数参数来自定义树的形状。
这个程序不仅能够帮助大家加深对C语言的理解,还能够锻炼编程的逻辑思维能力和实践能力。
希望大家能够充分利用这个程序来学习和掌握C语言的基本知识,进一步提高自己的编程能力。
总之,C语言是一门非常重要的编程语言,掌握它对自身的成长和未来职业发展都具有重要意义。
通过编写星号树状结构的程序,我们不仅可以加深对C语言的理解,还可以提升编程能力。
希望大家能够善加利用这个程序,并将学到的知识应用于实践中,不断完善自己的技能。
c语言编程爱心代码
c语言编程爱心代码作为一名初学者,很容易因为复杂的代码而放弃学习编程。
但是,对于爱编程的人来说,编程就像呼吸一样自然。
那么,在学习C语言编程的过程中,如何编写爱心代码?下面是一些基本步骤。
第一步:打开编译器首先,你需要打开一个编译器来编写你的C程序。
在这里,我们建议使用Visual Studio Code,这是一款免费的、开源的代码编辑器。
它不仅具有功能强大的编辑器和调试器,还可以轻松访问各种扩展和插件。
第二步:编写程序现在,你可以开始编写你的C程序了。
首先,我们需要定义一个函数,用于绘制心形。
以下是实现这一功能的代码:void drawHeart(){int x, y;double f;for (y = 20; y >= -20; y--){for (x = -30; x <= 30; x++){f = (double)x * x + (double)y * y - 900;if (f <= 0){putchar('*');}else{putchar(' ');}}putchar('\n');}}在这个函数中,我们使用两个for循环来遍历坐标系中的每一个位置。
对于每个位置,我们计算它到心形曲线的距离。
如果距离小于等于零,则在该位置绘制一个星号。
第三步:调用函数现在,我们需要在主函数中调用drawHeart()。
以下是如何实现的:int main(){drawHeart();return 0;}这个程序只有几行代码,但它可以绘制一个美丽的心形图案。
当你运行程序时,你会看到一个绘制了一个心形在控制台屏幕上。
以上就是如何编写一个C语言编程的爱心代码的基本步骤。
当然,这只是一个简单的例子,你可以为自己喜欢的图案编写相关函数。
无论你选择什么样的图案,只要你有爱心,你就可以设计出美丽的代码。
c语言的语法规则
c语言的语法规则
C语言是一种计算机程序设计语言,其语法规则如下:
1. 语句必须以分号(;)结束。
2. 单行注释用两个斜杠(//)表示,多行注释用斜杠和星号(/*...*/)表示。
3. 关键字(如if、while、int等)不能作为变量名。
4. 变量必须先定义后使用,定义时必须指定类型(如int、float等)。
5. 变量的名字只能由字母、数字和下划线(_)组成,开头必须是字母或下划线。
6. 变量可以被赋值,赋值号(=)表示赋值操作。
7. 表达式是指值和运算符组成的式子,可以用于计算。
8. 函数是指一组语句的集合,有一个名字和可以接受输入参数的定义。
9. 常量是指值不变的量,可以用#define定义。
10. 控制语句有if、else、for、while和switch等,用于改变程序的执行流程。
以上是C语言的基本语法规则,了解和掌握这些规则可以帮助我们更好地编写C程序。
c语言星空代码
c语言星空代码C语言星空代码,是一段代码用来输出一颗星星,颇受程序员喜爱。
在程序执行过程中,输出的结果和一颗闪烁的星星很相似,因此也被称为星空代码。
下面将介绍一下C语言星空代码的实现逻辑和编写方法。
实现逻辑C语言星空代码的实现逻辑比较简单。
程序会输出一个很长的字符串,其中每个字符都代表星星的一颗点。
根据不同的字符,输出的效果也不同。
一般情况下,我们用空格来表示黑暗的夜空,用“*”来表示星星的一颗点。
如果打印垂直方向的星星,则需要在ASCII码中选择输出一个竖线“|”,表示星星正立。
而打印倾斜的星星,则需要输出ASCII码中“\”或“/”符号。
编写方法编写C语言星空代码,首先需要确定输出的字符串长度。
一般情况下,我们选用宽度为80个字符,高度为25行的终端屏幕作为输出界面。
因此,字符串长度应该是80*25=2000个字符。
这个字符串中,每个字符都代表星星的一颗点,可以用字符数组存储。
在程序中,我们可以用两层循环,根据不同的情况输出星星。
首先,我们需要定义一个字符数组并初始化。
可以使用下面的语句进行初始化:char star[2000] = " ";其中,双引号内的内容就是2000个空格,用来表示黑暗的夜空。
接下来,我们需要在数组上添加星星。
可以使用一些特殊的字符来表示不同的星星情况,例如空格,竖线,反斜杠和斜杠等。
然后,根据不同的字符,使用条件判断语句将不同的字符添加到数组中。
可以通过调整循环中计数器的值,来产生渐变的效果,让星星闪烁。
最后,我们需要在终端屏幕中输出这个字符数组。
可以使用for循环将数组中的字符逐一输出,或者使用printf语句输出整个字符串。
代码示例下面是一段C语言星空代码的示例,可以输出闪烁的星星:```#include <stdio.h>#include <unistd.h>int main(){int i, j;char star[2000] = " "; while (1) {for (i = 0; i < 80; i++) {for (j = 0; j < 25; j++) {int index = j * 80 + i;if ((i + j) % 2 == 0) {star[index] = '*';}}}system("clear");printf("%s", star);usleep(200000);for (i = 0; i < 80; i++) {for (j = 0; j < 25; j++) {int index = j * 80 + i;if ((i + j) % 2 == 0) {star[index] = ' ';}}}printf("%s", star);usleep(200000);}return 0;}```这段代码使用双循环,将所有奇数位置(i+j为奇数)的字符改为星星,偶数位置则为黑色背景。
c语言星号打印矩形、三角形、菱形等图案及参考答案
c语⾔星号打印矩形、三⾓形、菱形等图案及参考答案⽤星号打印各种图形及参考答案欧阳学⽂【4.4】输⼊n值,输出如图所⽰矩形。
【4.5】输⼊n值,输出如图所⽰平⾏四边形。
【4.6】输⼊n值,输出如图所⽰⾼为n的等腰三⾓形。
【4.7】输⼊n值,输出如图所⽰⾼为n的等腰三⾓形。
【4.8】输⼊n值,输出如图所⽰⾼和上底均为n 的等腰梯形。
【4.9】输⼊n值,输出如图所⽰⾼和上底均为n 的等腰空⼼梯形。
【4.10】输⼊n值,输出如图所⽰边长为n的空⼼正六边型。
【4.11】输⼊n值,输出如图所⽰图形。
【4.12】输⼊n值,输出如图所⽰图形。
【4.13】输⼊n值,输出如图所⽰图形。
【4.14】输⼊n值,输出如图所⽰图形。
【4.15】输⼊n值,输出如图所⽰图形。
【4.16】输⼊n值,输出如图所⽰图形。
(例为n=6时)【4.17】编写程序,输出如图所⽰sin(x) 函数0到2π的图形。
【4.18】编写程序,在屏幕上输出⼀个由*号围成的空⼼圆。
【4.19】编写程序,在屏幕上绘制如图余弦曲线和直线。
若屏幕的横向为x轴,纵向为y轴,在屏幕上显⽰0~360度的cos(x)曲线与直线x=f(y)=45*(y1)+31的迭加图形。
其中cos图形⽤"*"表⽰,f(y)⽤"+"表⽰,在两个图形的交点处则⽤f(y)图形的符号。
【4.4】分析:打印此图形⽤两重循环实现。
图形要重复n⾏,故采⽤循环结构实现循环n次,循环体内部打印⼀⾏'*'号,把上述思路表⽰为:for(i=1;i<=n;i++)打印⼀⾏'*'号;每⾏有n个'*'号,再采⽤循环结构实现n次循环,循环内部⽤格式输出语句打印⼀个'*'号,即:for(j=1;j<=n;j++)printf("*");按照上述思路,实现打印矩形。
参考答案:main()printf("\nPlease Enter n:");scanf("%d",&n);for(i=1;i<=n;i++){ for(j=1;j<=n;j++)printf("*");printf("\n");}}【4.5】分析:此图形和上题的区别在于在每⼀⾏先要打印空格,然后再打印n个'*'号,在上题第⼀层循环体内打印'*'号的循环前⾯增加⼀个循环打印空格。
C语言 显示星号图形
显示星号图形显示的是直角边靠右的直角三角形。
#include<stdio.h>int main(){ int m,n=10;for(m=0;m<n;m++){ printf("%*.*s\n",n,m,"***********************");/*每行显示m个,每行占n个位置,左留空格*/ }return 0;}显示的是直角边靠左的直角三角形。
#include<stdio.h>int main(){ int m,n=10;for(m=0;m<n;m++){ printf("%-*.*s\n",n,m,"***********************");/*每行显示m个,每行占n个位置,右留空格*/ }return 0;}显示的是上小下大的等腰三角形。
#include<stdio.h>int main(){ int m,n=10;for(m=0;m<n;m++){ printf("%.*s",n-m," ");/*每行显示n-m个空格*/ printf("%.*s\n",2*m+1,"*************************");/*每行接着显示2m+1个*号*/ }return 0;}显示的是上大下小的等腰三角形。
#include<stdio.h>int main(){ int m,n=10;for(m=n-1;m>=0;m--){ printf("%.*s",n-m," ");printf("%.*s\n",2*m+1,"************************");}return 0;}/*与上题相比,将m的循环倒过来!*/显示菱形#include<stdio.h>int main(){ int n,i,m,bn,sn;printf("n(<22) : "); /*1 提示并*/scanf("%d",&n); /* 读取菱形行数n */for(i=1;i<=n;i++) /*2 循环:统一处理上、下两部分*/{ m=i<n+1-i?i:n+1-i; /*3 m=行号和倒数行号中的较小者*/ bn=(n+1)/2-m; sn=2*m-1; /*4 计算第m行空格数bn和星号数sn*/ printf("%*.*s\n",bn+sn,sn, /*5 显示bn个空格,sn个星号和换行*/ "*****************************************");}return 0;}。
C语言写的各种心形图案
C语言写的各种心形图案1./*高手在民间,只能说这个是人才写的*/#include "stdio.h"void main(){printf(" 我我\n 爱爱爱爱\n 你你你你\n");printf(" 我我我\n爱爱\n 你你\n");printf(" 我我\n 爱爱\n 你你\n");printf(" 我我\n 爱爱\n 你你\n");printf(" 我我\n 爱爱\n你\n");}/*输出结果:----------------------我我爱爱爱爱你你你你我我我爱爱你你我我爱爱你你我我爱爱你你我我爱爱你----------------------*/2./*结合课本输出几何图形*/#include <stdio.h>int main(){int i,j;printf(" ****** ******\n" " ********************\n" " ************* *************\n"); //前三排的规律性不强所以直接显示就好了for(i=0;i<3;i++)//显示中间三排{for(j=0;j<29;j++)printf("*");printf("\n"); }for(i=0;i<7;i++)//显示呈递减趋势规律的中间7排{for(j=0;j<2*(i+1)-1;j++)printf(" ");for(j=0;j<27-i*4;j++)printf("*");printf("\n"); }for(i=0;i<14;i++)//最后一个星号*与上面的规律脱节了所以独立显示printf(" ");printf("*\n");return 0;}/*------------------------------****** **************** *********************** ****************************************************************************************************************************************************------------------------------*/3./*双心*/#include<stdio.h>#include<math.h>void main(){int a,b,c;for(a=1;a<=6;a++){for(b=1;b<=6-a;b++)printf(" ");for(c=1;c<=2*a-1;c++){if(a<5&&(c==1||c==2*a-1)||(a==5&&(c==2||c==5||c==8))||a==6&&( c==4||c==5||c==7||c==8))printf("\3");elseprintf(" ");}printf("\n");}for(a=1;a<=6;a++){for(b=1;b<=a;b++)printf(" ");for(c=1;c<=11-2*a;c++){if(a>1&&(c==1||c==11-2*a)||a==1&&(c==2||c==5||c==8)) printf("\3");elseprintf(" ");}printf("\n");}}/*输出结果:---------------.. .. .. .. . ... ... . .. .. .. ..--------------- */4./*心形*/#include<stdio.h>#include<math.h>void main(){int a,b,c;for(a=1;a<=6;a++){for(b=1;b<=6-a;b++)printf(" ");for(c=1;c<=2*a-1;c++){if(a<5&&(c==1||c==2*a-1)||(a==5&&(c==2||c==5||c==8))||a==6&&( c==4||c==5||c==7||c==8))printf("\3");else printf(" ");}printf("\n");}}/*输出结果:------------------------------ .. .. .. .. . ... ..------------------------------ */。
c语言星号打印矩形、三角形、菱形等图案及参考答案
用星号打印各种图形及参考谜底之勘阻及广创作时间:二O二一年七月二十九日【4.4】输入n值,输出如图所示矩形.【4.5】输入n值,输出如图所示平行四边形.【4.6】输入n值,输出如图所示高为n的等腰三角形.【4.7】输入n值,输出如图所示高为n的等腰三角形.【4.8】输入n值,输出如图所示高和上底均为n的等腰梯形.【4.9】输入n值,输出如图所示高和上底均为n的等腰空心梯形.【4.10】输入n值,输出如图所示边长为n的空心正六边型.【4.11】输入n值,输出如图所示图形.【4.12】输入n值,输出如图所示图形.【4.13】输入n值,输出如图所示图形.【4.14】输入n值,输出如图所示图形.【4.15】输入n值,输出如图所示图形.【4.16】输入n值,输出如图所示图形.(例为n=6时)【4.17】编写法式,输出如图所示sin(x) 函数0到2π的图形.【4.18】编写法式,在屏幕上输出一个由*号围成的空心圆.【4.19】编写法式,在屏幕上绘制如图余弦曲线和直线.若屏幕的横向为x轴,纵向为y轴, 在屏幕上显示0~360度的cos(x)曲线与直线x=f(y)=45*(y-1)+31的迭加图形.其中cos图形用"*"暗示,f(y)用"+"暗示,在两个图形的交点处则用f(y)图形的符号.【4.4】分析:打印此图形用两重循环实现.图形要重复n行,故采纳循环结构实现循环n次,循环体内部打印一行'*'号,把上述思路暗示为:for(i=1;i<=n;i++)打印一行'*'号;每行有n个'*'号,再采纳循环结构实现n次循环,循环内部用格式输出语句打印一个'*'号,即:for(j=1;j<=n;j++)printf("*");依照上述思路,实现打印矩形.参考谜底:main(){ int i,j,n;printf("\nPlease Enter n:");scanf("%d",&n);for(i=1;i<=n;i++){ for(j=1;j<=n;j++)printf("*");printf("\n");}}【4.5】分析:此图形和上题的区别在于在每一行先要打印空格,然后再打印n个'*'号,在上题第一层循环体内打印'*'号的循环前面增加一个循环打印空格.每行空格的个数是逐行减少的,由于第一层循环的控制变量i是逐行增1,所以用一个固定值的数减去i 就可实现对空格个数的控制,在此题中固定值可使用变量n.参考谜底:main( ){ int i,j,n;printf("\nPlease Enter n:");scanf("%d",&n);for(i=1;i<=n;i++){ for(j=1;j<=n-i;j++)printf(" ");for(j=1;j<=n;j++)printf("*");printf("\n");}}【4.6】分析:此题和上题的区别在于每行'*'的数量逐行减少,可以使用上题控制空格个数的思路来控制'*'号的个数,请注意每行'*'的个数都是奇数.参考谜底:main( ){ int i,j,n;printf("\nPlease Enter n:");scanf("%d",&n);for(i=1;i<=n;i++){ for(j=1;j<=n-i;j++)printf(" ");for(j=1;j<=2*i-1;j++)printf("*");printf("\n");}}【4.7】分析:此题图形是第3题图形的垂直反转,在编程上我们可以变换一个思路.对图形中的第i行(1≤i≤n),共需要输出2n-i个字符,其中前面的i-1个字符为空格,后面的字符为'*'号.依照这一思路可以编写出如下法式.参考谜底:main( ){ int i,j,n;printf("\nPlease Enter n:");scanf("%d", &n);for( i=1;i<=n;i++ ) /* 重复输出图形的n行 */{ for( j=1;j<=2*n-i;j++ ) /* 重复输出图形一行中的每个字符 */if(j<=i-1) printf(" "); /* 输出前面的空格 */else printf("*"); /* 输出后面的*号 */printf("\n");}}【4.8】分析:此题和第3题的区别仅是每行的'*'个数增加n-1个.参考谜底:main( ){ int i,j,n;printf("\nPlease Enter n:");scanf("%d",&n);for(i=1;i<=n;i++){ for(j=1;j<=n-i;j++)printf(" ");for(j=1;j<=2*i-1+(n-1);j++)printf("*");printf("\n");}}【4.9】分析:对空心图形,我们可以在上题的基础上,对打印'*'号的循环进行修改,仅在循环开始值(j=1)和循环结束值(j=2*(i-1)+n)时打印'*'号,其它位置都打印空格.另一种思路是将每行打印的空格和'*'的两个循环合为一体考虑,在判断出需要打印'*'的两个位置及第一行和最后一行相应位置外,其余位置都打印空格.参考谜底:main( ){ int i,j,n;printf("\nPlease Enter n:");scanf("%d",&n);for(i=1;i<=n;i++){ for(j=1;j<=2*n+i-3;j++)if(j==n-i+1 || j>n-i+1 && (i==1||i==n)) printf("*");else printf(" ");printf("*\n");}}【4.10】分析:此图形可以理解为两个空心梯形反向连接而成,因此可以利用上题的思路进行输出.参考谜底:main( ){ int i,j,n;printf("\nPlease Enter n:");scanf("%d",&n);for(i=1;i<=n;i++) /* 输出图形的上半部份(含中心行) */ { for(j=1;j<=2*n-i-1;j++)if(j==i) printf("*");else printf(" ");printf("*\n");}for(i=1;i<n;i++) /* 输出图形的下半部份(不含中心行) */ { for(j=1;j<=n+i;j++)if(j==n-i) printf("*");else printf(" ");printf("*\n");}}【4.11】分析:此题与上题的区别在于打印'*'号的位置分歧,编程时要找出应打印'*'号的位置和两个循环变量i、j以及行数n的关系.参考谜底:main( ){ int i,j,n;printf("\nPlease Enter n:");scanf ("%d", &n);for(i=1;i<=n;i++) /* 输出图形的上半部份(含中心行) */ { for(j=1;j<=2*n-i;j++)if(j==n-i+1 || j>n-i+1 && i==1) printf("*");else printf(" ");printf("*\n");}for(i=1;i<n;i++) /* 输出图形的下半部份(不含中心行) */ { for(j=1;j<=3*(n-1)-i;j++)if(j==i+1 || j>i+1 && i==n-1) printf("*");else printf(" ");printf("*\n");}}【4.12】参考谜底:main( ){ int i,j,n;printf("\nPlease Enter n:");scanf("%d",&n);for(i=1;i<=n;i++){ for(j=1;j<=n;j++)if(j==n-i+1 || i==1 || i==n) printf("*");else printf(" ");printf("\n");}}【4.13】参考谜底:main( ){ int i,j,n;printf("\nPlease Enter n: ");scanf("%d", &n);for(i=1;i<=n;i++) /* 输出图形的上半部份(含中心行) */ { for(j=1;j<=n-i;j++)if(j==1 || j==n-i+1) printf("* ");else printf(" ");printf("\n");}for(i=1;i<n;i++) /* 输出图形的下半部份(不含中心行) */ { for(j=1;j<=i+1;j++)if(j==1 || j==i+1) printf("* ");else printf(" ");printf("\n");}}【4.14】参考谜底:main( ){ int i,j,n;printf("\nPlease Enter n: ");scanf("%d",&n);for(i=1;i<=n;i++){ for(j=1;j<=n;j++)if(j==1 || j==i || j==n) printf("*");else printf(" ");printf("\n");}}【4.15】参考谜底:main( ){ int i,j,n;printf("\nPlease Enter n: ");scanf("%d",&n);for(i=1;i<=n;i++){ for(j=1;j<=n+i-1;j++)if(j>n-i) printf("*");else printf(" ");printf("\n");}for(i=1;i<n;i++){ for(j=1;j<=2*n-i-1;j++)if(j>i) printf("*");else printf(" ");printf("\n");}}【4.16】参考谜底:main( ){ int i,j,n;printf("\nPlease Enter n: ");scanf("%d",&n);for(i=1;i<=n;i++){ for(j=1;j<=n+i-2;j++)if(j==n-i+1) printf("*");else printf(" ");printf("*\n");}}【4.17】分析:首先对图形进行设计,坐标的X轴和Y轴分别对应屏幕的列和行,一个正弦函数的周期为0~360度,我们把一个步长界说为10度,打印时每换一行即是函数的自变量增加10度;屏幕的列宽为80,函数值为0对应屏幕的第40列,sin(x)的值在-1~1,变换成列数为以0为中心的-30~30,对应屏幕上第10~70列.设计法式时,控制换行的自变量i乘以10获得正弦函数的X值,调用库函数sin()求出函数值再乘以30输出的列宽,因为我们以屏幕的第40列为0点,故再加上40获得应在屏幕上显示的点.参考谜底:#include <math.h>main( ){ double x;int y,i,yy;for(i=1;i<80;i++) /* 打印图形的第一行 */if(i==40) printf("*");/* i控制打印的列位置*/ else printf("-");printf("\n");for(x=10.0;x<=360.0;x+=10.) /* 从10度到360度 */{ y = 40+30*sin(x*PAI/180.0); /* 计算对应的列 */yy = 40>y ? 40 : y; /* 下一行要打印的字符总数 */for (i=1;i<=yy;i++) /* 控制输出图形中的一行 */{ if(i==y) printf("*"); /* i控制打印的列位置 */else if(i==40) printf("|"); /* 打印中心的竖线 */else printf(" ");}printf("\n");}}【4.18】分析:首先设计屏幕图形,如果预计圆形在屏幕上打印20行,所以界说圆的直径就是20,半径为10,圆的方程是X2×Y2=R2,因为图形不是从中心开始打印而是从边缘开始,所以Y 从10变动到-10,根据方程求出X,对求得的X值再根据屏幕行宽进行需要的调整获得应打印的屏幕位置.参考谜底:#include <math.h>main( ){ double y;int x,m;for(y=10;y>=-10;y--) /* 圆的半径为10 */{ m = 2.5 * sqrt(100-y*y); /* 计算行y对应的列坐标m */ for(x=1;x<30-m;x++)printf(" "); /* 输出圆左侧的空白 */ printf("*"); /* 输出圆的左侧 */for(;x<30+m;x++)printf(" "); /* 输出圆的空心部份 */ printf("*\n"); /* 输出圆的右侧 */}}【4.19】参考谜底:#include <stdio.h>#include <math.h>main( ){ double y;int x, m, n, yy;for( yy=0;yy<=20;yy++){ y = 0.1*yy;m = acos(1-y)*10;n = 45 * (y-1)+31;for( x=0;x<=62;x++ )if( x==m && x==n ) printf("+");else if(x==n) printf("+");else if(x==m || x==62-m) printf("*");else printf(" ");printf("\n");}}。
c语言字符相乘
c语言字符相乘C语言是一门广泛使用的编程语言,其中涵盖了很多基本的编程概念。
在C语言中,字符相乘是一种较为基础的操作,但对于初学者来说可能会比较困难,因此本文将为大家讲解一下C语言中字符相乘的相关知识。
首先,我们需要了解什么是字符。
在C语言中,字符是一种基本的数据类型,它可以表示任何一个ASCII字符(即数字、字母、符号等)。
在代码中,我们使用单引号将字符括起来表示字符类型。
例如:char ch = 'A';这一行代码定义了一个字符变量ch,并将其赋值为大写字母A。
接下来,我们来看一下C语言中的乘法运算符。
在C语言中,乘法运算符使用星号(*)表示,用于将两个数相乘。
例如:int x = 2;int y = 3;int result = x * y;这个例子中,我们定义了两个整数变量x和y,将它们相乘后赋值给了另外一个整数变量result。
在运行这段代码时,result变量的值为6。
现在,让我们来看看C语言中的字符相乘。
在C语言中,字符相乘是指使用乘法运算符将两个字符相乘。
由于C语言认为字符类型可以转换成整数类型,因此在字符相乘时,实际上是将字符的ASCII码值相乘后得到一个整数值。
如果要将两个字符相乘,我们需要将它们转换成整数类型,然后再相乘。
例如:char ch1 = 'A';char ch2 = 'B';int result = ch1 * ch2;在这个例子中,我们定义了两个字符类型变量ch1和ch2,并将它们相乘后赋值给了一个整数变量result。
由于字符类型的变量可以转换成整数类型的变量,所以在执行乘法运算时,C语言会将字符的ASCII码值相乘得到一个整数值。
在这个例子中,ch1对应的ASCII码值为65,ch2对应的ASCII码值为66,所以相乘后的结果为4290(65*66=4290),将这个结果赋值给result变量。
需要注意的是,由于字符相乘得到的结果是一个整数类型的值,因此在将结果赋给一个字符类型的变量或在printf函数中输出结果时,需要将其转换成字符类型,否则结果将会输出一个乱码字符。
c语言中指针前面的星号,什么时候可以省去,什么时候又必须带上呢?
c语言中指针前面的星号,什么时候可以省去,什么时候又必
须带上呢?
最佳答案
其实没那么复杂。
主要是区别于在声明定义的时候,有的人会迷惑,要不要加*
如下
int *p
p=&x;//此处明明是p=&x,好往下看
int *p=&x//其实在声明的时候这样也是可以的。
但是这样写定义不明确。
我们现在来总结一下,在定义的时候*号,只是一个说明符。
意义是告诉你p是一个指针,而不是一个其他数。
在声明的时候就一定需要*了,
所以请注意上面的对比。
在引用的时候区别就相当简单了
p是指针变量,指的是一个变量的地址。
*p代表的是所指向的这个变量的值。
举例:
int a=3;
int *p
p=&a;
printf("%d%d",*p,p);
这个时候两个输出的值,第一个就是3(变量的值),第二个输出的是变量a存储的地址单位。
楼主要是还有疑问可以一起讨论。
c语言小星星编程,《C语言及程序设计》实践参考——输出小星星(全解)
c语⾔⼩星星编程,《C语⾔及程序设计》实践参考——输出⼩星星(全解)《C语⾔及程序设计》实践参考——输出⼩星星(全解)《C语⾔及程序设计》实践参考——输出⼩星星(全解)返回:贺⽼师课程教学链接 项⽬要求(1)要输出的是:代码:#includeint main( ){int i,j,n=6;for(i=n;i>=1;--i) //⼀共要输出n⾏{//输出第i⾏for(j=1; j<=2*i-1; ++j) //输出2*i-1个星号printf("*");printf("\n");}return 0;}(2)要输出的是:代码:#includeint main( ){int i,j,n=6;for(i=1;i<=n;++i) //⼀共要输出n⾏{//输出第i⾏for(j=1; j<=n-i; ++j) //输出n-i个空格printf(" ");for(j=1; j<=i; ++j) //输出i个星号printf("*");printf("\n");}return 0;}(3)要输出的是:代码:int main( ){int i,j,n=6;for(i=n;i>=1;--i) //i由⼤变⼩{//输出第i⾏for(j=1; j<=n-i; ++j) //关键:输出的是n-i个空格printf(" ");for(j=1; j<=2*i-1; ++j) //关键:输出的是2*i-1个星号printf("*");printf("\n");}return 0;}(4)要输出的是:代码:#includeint main( ){int i,j,n=6;for(i=1;i<=n;++i) //⼀共要输出n⾏{//输出第i⾏for(j=1; j<=n-i; ++j) //输出n-i个空格for(j=1; j<=2*i-1; ++j) //输出2*i-1个星号printf("*");printf("\n");}return 0;}(5)要输出的是:代码:这⼀个稍微⿇烦⼀些在于,第1⾏和最后⼀⾏单独处理,⽽中间的n-2⾏则有规律:若⼲空格、1个星号、若⼲空格、1个星号#includeint main( ){int i,j,n=6;//输出第⼀⾏:n-1个空格和1个星号并换⾏for(j=1; j<=n-1; ++j) //输出n-i个空格printf(" ");printf("*\n");//再输出中间的n-2⾏for(i=2;i<=n-1;++i) //⼀共要输出n-2⾏{//输出第i⾏for(j=1; j<=n-i; ++j) //输出n-i个空格printf(" ");printf("*");; //再输出⼀个星号for(j=1; j<=2*i-3; ++j) //然后输出2*i-3个空格printf("*\n"); //输出⼀个星号后本⾏结束,换⾏}//输出最后⼀⾏:2*n-1个星号for(j=1; j<=2*n-1; ++j)printf("*");printf("\n");return 0;}(6)要输出的是:参考代码:#includeint main( ){int i,j,n=6; //n代表上三⾓⾏数//先输出上三⾓for(i=1;i<=n;++i) //输出n⾏{//输出第i⾏for(j=1; j<=n-i; ++j) //输出n-i个空格printf(" ");for(j=1; j<=2*i-1; ++j) //输出2*i-1个星号printf("*");printf("\n");}//下⾯输出下三⾓for(i=1;i<=n-1;++i) //输出n-1⾏{//输出第i⾏for(j=1; j<=i; ++j) //输出i个空格printf(" ");for(j=1; j<=2*(n-i)-1; ++j) //输出2*i-1个星号printf("*");printf("\n");}return 0;}《C语⾔及程序设计》实践参考——输出⼩星星(全解)相关教程。
c语言次方符号
c语言次方符号C语言是一种广泛应用于计算机编程的高级编程语言,它具有简洁、高效、灵活等特点,被广泛用于开发各种软件和系统。
在C语言中,有一个非常重要的运算符号,那就是次方符号。
次方符号用来表示一个数的幂次运算,可以方便地进行数值计算和科学计算。
在C语言中,次方符号使用两个星号(**)表示,它的作用是将一个数的指定次方计算出来。
例如,2的3次方可以表示为2**3,结果为8。
这个运算符号非常简单,但却非常实用,可以用来解决很多实际问题。
次方符号在数学和物理等领域有着广泛的应用。
在数学中,次方符号可以用来计算多项式的展开式,求解方程等。
在物理中,次方符号可以用来计算物体的速度、加速度、功率等。
在计算机科学中,次方符号可以用来进行数据加密、图像处理、模拟仿真等。
使用次方符号进行数值计算非常简单。
只需要将底数和指数用次方符号连接起来即可。
例如,计算2的4次方可以写为2**4,结果为16。
同样地,计算3的2次方可以写为3**2,结果为9。
次方符号可以用于整数、浮点数和负数等不同类型的数值计算。
除了次方符号,C语言还提供了一些其他的数学函数和运算符号,用于进行更加复杂的数值计算。
例如,sqrt函数可以用来计算一个数的平方根,pow函数可以用来计算一个数的任意次方。
这些函数和运算符号可以帮助我们更加方便地进行数值计算和科学计算。
在实际编程中,次方符号可以用于解决很多实际问题。
例如,我们可以使用次方符号来计算一个数的阶乘。
阶乘是指从1到该数的连续整数相乘的结果。
使用次方符号,我们可以很方便地计算出一个数的阶乘。
例如,计算5的阶乘可以写为5**1 * 5**2 * 5**3 * 5**4 * 5**5,结果为120。
除了阶乘,次方符号还可以用于计算数列的和。
数列是指按照一定规律排列的一组数。
使用次方符号,我们可以很方便地计算出数列的和。
例如,计算1到10的平方和可以写为1**2 + 2**2 + 3**2 + ... +10**2,结果为385。
C语言特殊符号意义
C语言中像%D &%f符号的作用说一下最佳答案C语言中的符号运算符的种类C语言的运算符可分为以下几类:1.算术运算符用于各类数值运算。
包括加(+)、减(-)、乘(*)、除(/)、求余(或称模运算,%)、自增(++)、自减(–)共七种。
2.关系运算符用于比较运算。
包括大于(>)、小于(<)、等于(==)、大于等于(>=)、小于等于(<=)和不等于(!=)六种。
3.逻辑运算符用于逻辑运算。
包括与(&&)、或(||)、非(!)三种。
4.位操作运算符参与运算的量,按二进制位进行运算。
包括位与(&)、位或(|)、位非(~)、位异或(^)、左移(<<)、右移(>>)六种。
5.赋值运算符用于赋值运算,分为简单赋值(=)、复合算术赋值(+=,-=,*=,/=,%=)和复合位运算赋值(&=,|=,^=,>>=,<<=)三类共十一种。
6.条件运算符这是一个三目运算符,用于条件求值(?:)。
7.逗号运算符用于把若干表达式组合成一个表达式(,)。
8.指针运算符用于取内容(*)和取地址(&)二种运算。
9.求字节数运算符用于计算数据类型所占的字节数(sizeof)。
10.特殊运算符有括号(),下标[],成员(→,.)等几种。
1.C的数据类型基本类型,构造类型,指针类型,空类型2.基本类型的分类及特点类型说明符字节数值范围字符型char 1 C字符集基本整型int 2 -32768~32767短整型short int 2 -32768~32767长整型 long int 4 -214783648~214783647无符号型 unsigned 2 0~65535无符号长整型 unsigned long 4 0~4294967295单精度实型 float 4 3/4E-38~3/4E+38双精度实型 double 8 1/7E-308~1/7E+3083.常量后缀L或l 长整型U或u 无符号数F或f 浮点数4.常量类型整数,长整数,无符号数,浮点数,字符,字符串,符号常数,转义字符。
c语言各个符号的意思及用法
c语言各个符号的意思及用法C语言中有很多符号,以下是其中一些常见符号的含义及用法:1. 变量名、函数名:通常由字母、数字和下划线组成,不能以数字开头。
例如:```cint age = 20; // 定义一个整型变量 age,并赋值为 20void printMessage() { // 定义一个名为 printMessage 的函数printf("Hello, world!\n"); // 输出 "Hello, world!"}```2. 运算符:用于进行各种运算,例如加、减、乘、除等。
例如:```cint sum = 5 + 3; // 将 5 和 3 相加,结果赋给变量 sumint product = 4 * 2; // 将 4 和 2 相乘,结果赋给变量product```3. 控制语句:用于控制程序的流程,例如 if、for、while 等。
例如:```cif (age > 18) { // 如果 age 大于 18,则执行以下代码块printf("You are an adult.\n"); // 输出 "You are an adult."} else { // 如果 age 小于等于 18,则执行以下代码块printf("You are a minor.\n"); // 输出 "You are a minor."}```4. 分号:用于表示语句的结束。
例如:```cint x = 5; // 定义一个整型变量 x,并赋值为 5```5. 大括号:用于定义代码块。
例如:```cif (x > 10) { // 如果 x 大于 10,则执行以下代码块printf("x is greater than 10.\n"); // 输出 "x is greater than 10."} else { // 如果 x 小于等于 10,则执行以下代码块printf("x is less than or equal to 10.\n"); // 输出 "x is less than or equal to 10."}```。
c语言中指数运算
c语言中指数运算C语言中的指数运算在数学中被称为乘幂运算。
它是一种将基数提高至指定幂次的操作。
例如,2的3次方等于8,这个操作可以用C语言的运算符来表示为2 ** 3。
C语言的指数运算符是双星号(**),用来表示底数与指数的乘幂运算。
这个运算符也可以用pow()函数来实现。
pow()函数需要两个参数:一个是底数,另一个是幂次。
下面是一个用指数运算符实现幂运算的例子:#include <stdio.h>int main() { int base, exponent, result; printf("Enter base number: "); scanf("%d",&base);printf("Enter exponent: "); scanf("%d",&exponent);result = 1; while (exponent != 0){ result *= base; --exponent; } printf("Answer = %d", result); return0; }在这个例子中,我们使用指数运算符来计算给定基数和幂次的幂运算。
程序首先提示用户输入基数和幂次,然后使用while循环重复基数的乘法运算,直到幂次变为0为止。
最后,程序输出计算结果。
另一种实现幂运算的方法是使用数学库函数pow()。
下面的代码演示如何使用pow()函数进行幂运算:#include <stdio.h> #include <math.h>int main() { double base, exponent, result; printf("Enter base number: "); scanf("%lf",&base);printf("Enter exponent: "); scanf("%lf",&exponent);result = pow(base, exponent);printf("%.2f^%.2f = %.2f", base, exponent, result); return 0; }在这个例子中,我们使用双星号运算符来计算给定基数和幂次的幂运算。
C语言各类符号意思,新手小白收藏好文,看了必懂
C语言各类符号意思,新手小白收藏好文,看了必懂auto :声明自动变量一般不使用double :声明双精度变量或函数int:声明整型变量或函数struct:声明结构体变量或函数break:跳出当前循环else :条件语句否定分支(与 if 连用)long :声明长整型变量或函数switch :用于开关语句case:开关语句分支enum :声明枚举类型register:声明积存器变量typedef:用以给数据类型取别名(当然还有其他作用)char :声明字符型变量或函数extern:声明变量是在其他文件正声明(也可以看做是引用变量)return :子程序返回语句(可以带参数,也看不带参数)union:声明联合数据类型const :声明只读变量float:声明浮点型变量或函数short :声明短整型变量或函数unsigned:声明无符号类型变量或函数continue:结束当前循环,开始下一轮循环for:一种循环语句(可意会不可言传)signed:生命有符号类型变量或函数void :声明函数无返回值或无参数,声明无类型指针(基本上就这三个作用)default:开关语句中的“其他”分支goto:无条件跳转语句sizeof:计算数据类型长度volatile:说明变量在程序执行中可被隐含地改变do :循环语句的循环体while :循环语句的循环条件static :声明静态变量if:条件语句C语言中的符号运算符的种类C语言的运算符可分为以下几类:1.算术运算符用于各类数值运算。
包括加(+)、减(-)、乘()、除(/)、求余(或称模运算,%)、自增(++)、自减(–)共七种。
2.关系运算符用于比较运算。
包括大于(>)、小于(<)、等于(==)、大于等于(>=)、小于等于(<=)和不等于(!=)六种。
3.逻辑运算符用于逻辑运算。
包括与(&&)、或(||)、非(!)三种。
4.位操作运算符参与运算的量,按二进制位进行运算。
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
星号的秘密1、乘法运算符2、定义指针int *p = 0; 还是int* p = 0;?后一种比较容易这样理解:定义了一个变量p,它是指针型的(更详细一点,是指向int的指针型),相比而言,前面一种定义似乎是定义了*P这个奇怪的东西。
但是后面一种写法会带来一个容易产生的误解:int* p1, p2;这儿给人的感觉似乎是定义了两个指针型变量p1和p2,但是,事实上,这种直觉是错误的,正确的理解方式是int *p1, p2;即p1是指针型的,而p2确是整型的。
在MS VC++ 6.0中,是按照后面一种格式写的。
3、何谓指针?指针仅仅表示一个内存中的某个地址?非也,注意到,我们在定义指针的时候,都关联了一个类型,如int,char,或者是string等等,如果说指针仅仅表示一个内存中的地址,那何必要关联这么多变化的东西呢?完全可以DWORD p=0;这样解决问题。
关联了的数据类型是作何用的呢?它可以指示编译器怎样解释特定地址上内存的内容,以及该内存区域应该跨越多少内存单元。
如int *p;编译器可以从这个定义中获得信息:1、p指向的内存存放的是整型数据,2、由于该内存区域只存放了一个数据,跨越的内存区域为4个字节,即p+1的效果是跳过了四个字节。
另一个复杂一点的例子,如struct a{int x1;short x2;a *next;}定义指针a *p;那么编译器对这个指针又作何解释呢?1、p指向的内存区域依次存放了三种类型的数据,分别是int,short和一个指针型数据。
2、p指向的内存区域跨越了12个字节,即p+1的效果是跳过了12个字节。
(为何不是10?对齐的原因)但是,C++中定义了一种特殊的指针,它去处了一般指针中对内存区域内容以及大小的解释,以满足特定定的需要,如我们只需要某块内存的首地址,不需要考虑其中的数据类型以及大小。
这种形式为void *; 这种类型的指针可以被任意数据类型的指针赋值,如上面的a* 型,void *q = p; 唯一例外的是,不能把函数指针赋给它。
4、关于const修饰符当const遇到指针,麻烦事就来了,看:const int* p; int* const p; const int* const p;这三个表达式,第一个表示p是一个指针,p本身平凡无比,但是p所指向的对象是一个特殊的对象--整型常量;第二个表示:这个p指针不是一个普通的指针,它是个常量指针,即只能对其初始化,而不能赋值,另外,这个指针所指向的对象是一平凡的int型变量;第三个则结合了前两者:指针和指向的对象都非同寻常,都是常量。
有了const,赋值的问题就变得麻烦起来,首先,对于const int* p;这儿由于p指向的对象是个常量,所以在通过p来引用这个对象的时候不可对其进行赋值!对于一个常量对象,不可以用普通的指针指向,而必须用这种指向常量的指针,原因很简单,通过普通指针可以改变指向的那个值,但是对于一个非常量对象,即普通变量,可不可以将其地址赋给指向常量的指针呢?是可以的,但是一旦这样指向之后,由于这个指针本身定义的是指向常量的指针,因而编译器统一认为其是指向变量的,因而此时不可以通过该指针修改所指向的对象的值。
第二,对于int* const p;这儿p本身是个常量指针,所以根本就不能赋值,所以不存在赋值的问题。
不可以用常量对其进行初始化,因为这个指针不是指向常量的;只能用变量对其初始化。
第三,对于const int* const p;这儿,只能初始化,不能赋值。
可以利用常量进行初始化;也可以利用变量对其初始化,不过不可以利用该指针对该变量进行赋值。
const int* p这种指向常量对象的指针常用来用作某些函数的形参,用意是从编译器的角度防止用户在函数中将传递进去的参数修改,虽然用户本身也可以避免,但是这样更可靠一点--当用户不小心作出修改实参的行为时,编译器发现并阻止这种行为。
this指针是const xx* const型的。
5、函数与指针指向函数的指针:可以利用它代替函数名来调用函数。
如何定义函数指针,由于一个程序中可以用多个函数名相同的情形(即函数的重载),因而,定义函数指针的时候,必须包含函数的参数,这样才能准确地将指针指向某函数。
定义:int (*p)(const char*, int); 表示p是一个指向函数的指针,该函数的两个参数为const char* 和int,另外该函数返回int型值。
容易混淆的是:int *p(const char *, int); 缺少了一个括号,此时编译器的解释是int* p(const char*, int);即其含义是一个函数的声明,函数名为p,返回一个指向int型的指针。
那么int* (*p)(const char*, int);则是定义了一个函数指针p,它指向一个函数,该函数的两个参数为const char*和int,该函数返回一个指向int型的指针函数指针的初始化与初始化:函数名如同数组名,编译器将其解释为指向该类型函数的指针,故而,可以领用函数名,或者&函数名对函数指针进行初始化或者赋值,另外,可以用另一个函数指针对该指针进行初始化以及赋值。
重要的一点是指针与函数名,指针与指针必须具有完全相同的参数表和返回类型(必须完全完全一样,任何一点不同都不可以)。
不存在隐式的类型转换,用户必须保证完全的一致性。
初始化或者赋值为0,表示不指向任何函数。
利用函数指针调用函数是可以p(x,y)这样调用,也可以(*p)(x,y)这样调用,前提是p已经正确的赋值或者初始化。
函数返回指针:可以返回一个非基本类型的对象。
6、数组与指针int a[3] = {1,2,3};考虑a,a[0], &a, 以及&a[0]这三个表达式的含义:首先这三个表达式的数值结果是一样的--数组的首地址(即数组中第0个元素的地址),但是编译器对三者的解释不同:对于a,编译器将其解释为一个指针,指向的是一个整型数据,因而利用a+1即指向数组中的第一的元素,a+2指向第二个元素。
对于a这个指针有些特殊的性质:a不是一个普通的指针,它同时是一个数组名,即关联了一个数组,因而某些性质上与普通的指针不同。
普通的指针可以被赋值,即可以用一个地址或者另一个指针修改当前指针的指向,然而对于a这种关联了一个数组的指针,如果允许这样赋值的话,那么数组中的元素将无法被访问,所以不允许对数组名代表的指针进行赋值。
在这一点上a相当于指针常量,即只能被初始化,不可以进行赋值。
虽然a不可以被赋值,但是将a赋给其他的元素是完全可以的,这一点同普通的指针没有不同。
综上,a相当于一个指针常量。
(type* const型的)本质上a[i]操作被编译器解释为*(a+i)操作,即[]运算符是通过数组名指针实现的,因而&a[0]的含义即&(*a),显然对一个指针先*(解引用),再&(引用),等价于什么都没做,还是这个指针本身,因而a完全等价于&a[o],--(&a[0])[i]等价于a[i],形式有点诡异,呵呵。
而对于&a 这个表达式,奇怪的是这个也是数组的首地址,那么就是说,这个数组的首地址中存放了一个指针常量(即数组名),但是数组的首地址中不是存放的一个int型的数字吗?这是怎么回事呢?难道一个地址能存放两个东西?暂时无法解释,可以这样认为编译器发现这种&和数组名的结合运算时,即返回数组首地址,只不过,这是,这仅仅是个纯粹的地址,它不再具有指针的特性,即编译器不再将其解释为指针,用户不可以通过+1运算来访问下一个数组元素。
它的+1就是数学上的+1。
当数组变为多维,问题变成怎么样了呢?考虑二维数组int b[4][3] = {{1,2,3}, {4,5,6}, {7,8,9}, {10,11,12}}; b,&b, b[0], &b[0], &b[0][0]几个表达式的含义:首先,c++中数组元素的存放是以行序为主序,即第一段存放第一行的数据,第二段存放第二行的数据,....,如此。
首先考虑数组名b,编译器同样将数组名b解释为一个指针,但是显然这个指针不是普通的指针。
这个b指向数组所有元素的首地址,这一点是勿庸置疑的,那么这个指针一步跨越的内存是多大呢?在本例中,b一步跨越12个字节,即b一步跨越数组中的一行元素,实际上b是一个指针的指针,或者说指向指针的指针,即b所指向的内容是一个指针,(同样对于b+1,b+2),b[i][j]这种访问方式本质上即:先通过+i,将指针跳跃到第i行,从而获得了指向第i行首地址的指针b[i],然后通过这个指针,再通过+j,跳跃j步,到达了第j个元素,即找到第i行,第j列的元素。
所以b是指针的指针,b[i]是指针,这儿,b[i]类似于一维中的a。
那么&b呢?&b仍然是数组的首地址,但是跟一维类似的是,这是个纯粹的地址,不再具有指针的特性,它的+1就是数学上的+1,不可以利用+1来访问下一个元素。
同样的道理对于&b[i],&运算符加上之后,本来是作为指针的b[i]被剥夺的指针的资格,返回一个纯粹的地址。
实际上,由于[]本质上是对指针的解引用,那么我们访问数组元素时可以不拘于a[i][j]这种方式,可以这样:(*(a+i))[j], 或者*(a[i]+j),或者*(*(a+i)+j),这几种写法是等价的。
对于&b[i][j]呢?我们把b[i][j]换一种写法,写成*(*(b+i)+j),这样问题就容易看清楚了,原来的*b[i][j]就等价于&(*(*(b+i)+j)),我们可以把最外层的括号脱掉,就成了*(b+i)+j,即b[i]+j,显然这是一个指针,指向第i行,第j列元素的指针,对该指针的解释是一次跨越一个int型的数据。
让我们再变态一点,考虑三维的情形,虽然三维的数组不多见,还是考虑一下吧,毕竟空间的坐标是用三维表示的。
int c[2][3][4] = {{{1,2,3,4},{5,6,7,8},{9,10,11,12}}, {{13,14,15,16},{17,18,19,20},{21,22,23,24}}};首先,数组名c,编译器将c解释为一个指针,指向数组的首地址,由于行序是主序,所以,该指针一步跨越12个整型数,共48个字节,实际上即跨越了一个二维数组。
对于&c,跟一维二维的情形类似,是一个纯粹的地址.c[i]呢?可以推测,c[i]与二维中的b类似,即指向指针的指针,c[i]一步跨越4个整数,16个字节。
c[i]是指向指针的指针,那么c便是指向指向指针的指针的指针(晕~)。