您的位置:首页 > 编程语言 > C语言/C++

C/C++的一些知识点归纳(二)

2017-03-19 19:57 253 查看
【1】输入输出

gets(str)输入的字符串中含有空格时,输出仍为全部字符串,这说明

gets() 函数不会把空格作为输入结束的标志,而只把回车换行作为输入结束的标志,这与 scanf() 函数是不同的。

总结:如果希望读取的字符串中不包含空格,那么使用 scanf() 函数;

如果希望获取整行字符串,那么使用 gets() 函数,它能避免空格的截断。

在 printf() 函数中使用%s输出字符串时,在变量列表中给出数组名即可,不能写为printf(“%s”, str[]);

【2】char *c 和char c[]

同样char *c = “abc”和char c[]=”abc”,前者改变其内容程序是会崩溃的,而后者完全正确。

char *string = "hello";//这样初始化之后,表示指针指向字符串常量,是只读的,不可改变。所以你再向string赋值,就会出错了。
//char *str, oldchar,newchar;//对str赋值,运行崩溃
char str[1000], oldchar,newchar;
scanf("%s %c %c",str,&oldchar,&newchar);


【3】

printf()函数的参数,在printf()函数读取时是从左往右读取的,然后将读取到的参数放到栈里面去,

最后读取到的就放在栈顶,处理参数的时候是从栈顶开始的,所以是从右边开始处理的.–printf()函数的特点.

  注意点:

  1.printf()函数中的计算是从右向左进行的.

  2.我们在写代码时,尽量避免无确定意义的表达式出现,因为不同的编译器,可能会采用不同的理解方式.

int main()
{
int a=2,b=2;
printf("%d---%d---%d\n",a<b,a>b,a==b); //0---0---1
a=2,b=3;
printf("%d---%d---%d\n",a<b,a>b,a==b);//1---0---0
a=2,b=3;
printf("%d---%d---%d\n",a<b,a>b,a!=b);//1---0----1
a=2,b=3;
printf("%d---%d---%d---%d---%d\n",a<b,a>b,a==b,a=b,a==b);  //0---0---1----3----0
}


【3】

c++中string类无法直接用scanf读取;

【4】string中find()函数

string z="0123456789";
cout<<z.find('5',0)<<endl;///   5


找到的是元素在字符串中的下标位置;

【5】

在字符串中‘\0’代表空字符,‘\0’ASCII值为0. 所以可认为‘\0’ == 0.

char a[]={‘1’,’2’,’3’,’4’,0,’5’};

strlen(a)=4;

【6】string 赋值问题

string的operator[]不会检查下标越界,而且用[]只能访问已存在的字符。

string str;
str[0]='1';//str开始默认为空 一开始未被分配
//定义的string str,只是一个空串,也就是长度为0,
//用任何的下标都会超过长度 。无法进行数组下标的赋值
cout<<"case1: "<<str<<endl;
str="abc";//可以整体赋值
cout<<"case2: "<<str<<endl;
str[0]='1';
str[2]='3';//str长度已经为1了,可以进行 str[0-2]的赋值
str[3]='c';
cout<<"case3: "<<str<<endl;


【7】动态分配数组测定

动态分配后的数组长度bytes 用 _msize() 测定。无法用sizeof(res[i])/sizeof(res[i][0])得到准确结果

_msize()取得malloc()分配的空间大小

★注意:该函数为Windows独有,UNIX没有对应的函数★

【8】指针自增

*n++ 是指针n加1

(*n)++表示n指向的内容加1

*n++里面的++是 n=n+1;

(*n)++里面的++是 *n = *n +1;

【9】二维指针的使用

int (*p)[4];//指针变量p指向包含4个整型元素的一维数组
*(p+i)+j //等价于&p[i][j];
*(*(p+i)+j)//等价于p[i][j];


【10】字符数组赋值

char a[15];

char b[10]=”1234”;

a=b不能这样直接赋值。

strcpy( a, b)进行赋值操作。

【11】n个平面最多把空间分成几份

思路:先考虑二维(直线)的情况,n个点把直线分成的份数a
=n+1。二维(平面)的情况,考虑n条直线把

一个平面分成的份数最多(表示为b
)时,第k条直线应该与前k-1条直线相交于不同的k-1个点,这k-1个点

将第k条直线分成a[k-1]部分,每一部分会把所在的平面分成两份,所以有b
=b[n-1]+a[n-1]。同理三维情况

c
=c[n-1]+b[n-1]。

f=f(n-1)+g(n-1) ps:g(n)=n(n+1)/2+1

=f(n-2)+g(n-2)+g(n-1)

……

=f(1)+g(1)+g(2)+……+g(n-1)

=2+(1*2+2*3+3*4+……+(n-1)n)/2+(n-1)

=(1+2^2+3^2+4^2+……+n^2-1-2-3-……-n )/2+n+1

=(n^3+5n)/6+1

【12】字符数组初始化的问题

char a[5]={“12345”};//[Error] initializer-string for array of chars is too long [-fpermissive] 用字符串初始化,要留出一位作为结束符’\0’

char A[5]={“1234”};//可行。

//等价于

char A[5]={‘1’,’2’,’3’,’4’,’\0’};

【13】字符连加最好拆开

string a="0";
a+=char('1')+char('1');
cout<<a<<endl;//0b a=a+{char('1')+char('1')}=a+'b';
string b="0";
b+=char('1');
b+=char('1');
cout<<b<<endl;//011


【14】三角函数

C中,三角函数的参数全部是弧度,不是常用的度,正弦30°的值的表达式是sin(30*PI/180.0),其中PI是π。

【15】数学常识

什么是数的因子?因子就是所有可以整除这个数的数,不包括这个数自身.因数包括这个数本身而因子不包括,如:

比如15的因子是1,3,5 而因数为1,3,5,15.

完数是指此数的所有因子之和等于此数,例如:28=1+2+4+7+14.

质数(prime number)又称素数

【16】scanf(“%f”,&a)和scanf(“%lf”,&b)

如果是 float a ; 用 scanf(“%f”,&a);

如果是 double a ; 用 scanf(“%lf”,&a);

建议都用 double,double是双精度,double有8个字节,float只有4个字节 lf可以理解成long f。

【17】

十的负六次方应表示为1E-6 或 1e-6 或直接表示为小数0.000001

if(a<1E-6)//a<0.000001
{
·······
}


【18】%的显示问题

%% 显示一个百分号。

scanf("%lf%%",&set);
scanf("%lf",&days);
printf("%f\n",days);
printf("%f%%\n",set);


【19】求绝对值abs()和fabs()

abs 返回整形数据的绝对值。

头文件:#include <math.h >

用 法: int abs(int i);

fabs 返回浮点数据的绝对值。

头文件:#include <math.h>

用法:extern float fabs(float x);

求绝对值的数据类型是整形就用abs,是浮点型就用fabs。

【20】malloc的使用

1. malloc函数位于stdlib.h中,用于向操作系统申请一块内存(动态分配内存),其原型为:

void* malloc(int size);

参数size用于指定需要申请的内存大小;返回值为一个指针,指向分配到的内存。

如果内存分配失败,函数的返回值为NULL,因此分配到内存后需要判断返回值。

例:分配一个包含n个元素的int数组

int a = (int ) malloc(sizeof(int) * n); /* 返回值需要强制类型转换 */

if (a == NULL) exit(1); /* 内存分配失败则结束程序,或另作处理 */

2. free函数也位于stdlib.h中,用于释放动态分配到的内存,其原型为

void free(void *ptr);

申请到的内存不再使用以后,应当及时释放。

3. 为一个int”二维数组”分配空间,首先应当分配一个int *指针的数组

int matrix = (int ) malloc(sizeof(int ) M);

然后再为每一个int *指针分配相应的int数组

for (i = 0; i < M; i++)
*(matrix + i) = (int *) malloc(sizeof(int) * N);
//  等价于matrix[i] = (int *) malloc(sizeof(int) * N)


然后才能用matrix[i][j]去访问/修改数据。实际上这个”二维数组”每一行是分布在内存中的不同位置,并不是连续存储的。

【21】结构体指针

struct student

{

int id, score;

};

struct student s, *p = &s, students[100];

scanf("%d%d", &p->id, &p->score);

printf("%d %d\n", p->id, p->score);

for (i = 0; i < 100; i++)

scanf("%d%d", &students[i].id, &students[i].score);

printf("%d %d\n", students[0].id, students[i].score);


【22】程序输入数据

把输入的 a b c m n 都用 printf 打出来看看,是不是遇到问题了?

== 思考 ==

对于下面这个代码,如果用户输入是 123回车 ,会有什么效果?为什么?

#include <stdio.h>

int main() {

int a;

char str[100];

scanf("%d", &a);

gets(str);

printf("a = %d, str = [%s]\n", a, str);

return 0;

}


== 分析 ==

若用户输入 123回车 ,则系统在输入缓冲区里头填入了4个字符 “123\n”。

scanf从输入缓冲区中读取了”123”三个数字字符后遇到”\n”,会将”\n”原封不动地留在缓冲区中,并将”123”转

换成整型存进变量a。

接下来执行gets(),它读取到的第一个字符是 “\n”,也就是遇到了“行末”,于是gets()在str[0]填入了一个’\0’就返回了。

所以程序的输出是 “a = 123, str = []”

== 解决 ==

1. 最直观的解决方案是,在 scanf(“%d”, &a); 后面加上一句 getchar(); 这样便能将剩下的一个 “\n” 字符给吃掉,就不会影响 gets() 函数的输入了。但问题是,如果用户输入的是 123空格回车 ,那么getchar()

读取到的就是空格,而回车仍然留在缓冲区中。

2. 另一个解决方案是,使用 scanf(“%d\n”, &a); 来进行输入。scanf会读入123对a赋值,然后读取并丢弃所

有空白字符,[直到]遇到一个非空白字符为止(该字符不会被读取,仍然留在缓冲区中)。

当我用 “%d\n” 调用 scanf 从键盘读取数字 的时候, 好像要多输入一行函数才返回。

可能令人吃惊, \n 在 scanf 格式串中不表示”等待换行符”, 而是读取并放弃所有的空白字符。

3. 对于Windows下的程序,可以使用fflush(stdin)去掉多余的回车等字符,但是对于Linux则无效。

【23】strcmp与strncmp

strcmp与strncmp都是用来比较字符串的,区别在于能否比较指定长度字符串。

strcmp

C/C++函数,比较两个字符串

设这两个字符串为str1,str2,

若str1==str2,则返回零;

若str1 > str2,则返回正数;

若str1< str2,则返回负数。

即:两个字符串自左向右逐个字符相比(按ASCII值大小相比较),直到出现不同的字符或遇’\0’为止。

strncmp函数是指定比较前maxlen个字符。

strncmp( )函数返回值:

此函数功能即比较字符串str1和str2的前maxlen个字符。如果前maxlen字节完全相等,返回值就=0;

在前maxlen字节比较过程中,如果出现str1
与str2
不等,则依次比较str1和str2的前n位,设i(i<n)为两字符串首次的不同位,则返回(str1[i]-str2[i])。

函数原型:int strncmp(char *str1, char *str2, int maxlen);

参数:

str1 指向第一个字符串的指针

str2 指向第二个字符串的指针

maxlen 比较的字符的个数,从第一个开始算
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  心得 知识点