C++学习基础篇
需要注意的点:
注意在使用函数的时候两种情况
1.值传递
此使不会改变实参的数值,只会改变形参的数值
2.地址传递
地址传递会改变实参的值。注意地址传递不是只有指针一种情况,目前还遇见了数组传递的情况,数组相当于是一个地址,可以近似理解成为一个指针,例如下面在函数中的应用
#include<iostream>
using namespace std;
struct hero
{
string name;
int age;
string sex;
};
void bubblesort(hero arr[], int a)
{
for (int i = 0; i < a-1; i++)
{
for (int j = 0; j < a - i - 1; j++)
{
if (arr[j].age > arr[j+1].age)
{
hero temp = arr[j];
arr[j] = arr[j + 1];
arr[j + 1] = temp;
}
}
}
}
void printhero(hero p[], int a)
{
for (int i = 0; i < a ; i++)
{
cout << p[i].name << p[i].age << p[i].sex << endl;
}
}
int main()
{
struct hero harr[5] =
{
{"刘备",23,"男"},
{"张飞",22,"男"},
{"关羽",21,"男"},
{"赵云",25,"男"},
{"黄忠",27,"男"},
};
int longth = sizeof(harr) / sizeof(harr[0]);
bubblesort(harr, longth);
printhero(harr, longth);
system("pause");
return 0;
}
创建函数时需要注意
一般用户自定义的函数要写在main函数之前,否则要提前声明,尽量写在main函数之前
结构体也一般定义在main函数之前
冒泡排序
void bubblesort(hero arr[], int a)
{
for (int i = 0; i < a-1; i++)
{
for (int j = 0; j < a - i - 1; j++)
{
if (arr[j].age > arr[j+1].age)
{
hero temp = arr[j];
arr[j] = arr[j + 1];
arr[j + 1] = temp;
}
}
}
}
数据的输入
语法: cin >> 变量
int a = 0;
cout << "请输入整型变量:" << endl;
cin >> a;
cout << a << endl;
switch语句常见错误
编译器错误 C2360
“identifier”初始化被“case”标签跳过
可以在 switch 语句中跳过 identifier 的初始化。 除非声明包含在块中,否则不能跳过带有初始值设定项的声明。 (除非在块中声明,否则变量在 switch 语句结束之前都在范围内。)
这是因为在case语句中有需要初始化的变量,比如此变量需要由cin输入时,会产生的错误
解决办法是把case语句用{ }包括起来变成一个块
结构体常见错误
警告 C26495
eg:变量 “variable” 未初始化。 始终初始化成员变量 (type.6)。
注解
成员变量不是由构造函数或初始化表达式初始化的。 请确保所有变量在构造结束时初始化。
下面的示例生成警告 C26495,因为创建 MyStruct 对象时未初始化成员变量 value。
struct MyStruct
{
int value;
MyStruct() {} // C26495, MyStruct::value is uninitialized
};
若要解决此问题,可以为所有成员变量添加类内初始化。
struct MyStruct
{
int value{}; // empty brace initializer sets value to 0
MyStruct() {} // no warning, MyStruct::value is set via default member initialization
};
即添加一个大括号,就可以解决这个问题,但是会将初始值设置为0
cin输入函数的某些错误情况
当定义int型时,例如:
int a;
cin>>a;
变量a是一个整形变量,当输入一个数字时,cin函数会将输入的数字赋值给a
但是,当输入字符时就会发生错误,且会进入不可预知的错误循环,例如
int inputsex = 0;
while (true)
{
cin >> inputsex;
if (inputsex == 1 || inputsex == 2)
{
p->personarr[p->renshu].sex = inputsex;
break;//如果输入1或2可以退出循环,否则要重新输入
}
else
{
cout << "wrong,please input sex again" << endl;
}
}
当输入字符时,程序在输出“wrong,please input sex again”后不会跳转到cin >> inputsex;部分,而是会无限输出“wrong,please input sex again”,为了解决这种情况的出现,可以加入以下部分:
cin.ignore()
默认值为1,可以在括号中输入任意数字,如5、100等,此函数的作用是跳过输入流中的 n 个字符
也可以输入一个字符,会跳过该字符前输入的部分
当同时输入时,哪个条件先满足就按哪个执行
cin.ignore(a,ch)方法是从输入流(cin)中提取字符,提取的字符被忽略(ignore),不被使用。每抛弃一个字符,它都要计数和比较字符:如果计数值达到a或者被抛弃的字符是ch,则cin.ignore()函数执行终止;否则,它继续等待。它的一个常用功能就是用来清除以回车结束的输入缓冲区的内容,消除上一次输入对下一次输入的影响。比如可以这么用:cin.ignore(1024,‘\n’),通常把第一个参数设置得足够大,这样实际上总是只有第二个参数’\n’起作用,所以这一句就是把回车(包括回车)之前的所以字符从输入缓冲(流)中清除出去。
如果cin.ignore()不给参数,则默认参数为cin.ignore(1,EOF),即把EOF前的1个字符清掉,没有遇到EOF就清掉一个字符然后结束,会导致不正确的结果,因为EOF是文件结束标识。
#include <iostream>
using namespace std;
int main()
{
int n;
cin.ignore(5, 'A');
cin >> n;
cout << n;
return 0;
}
当输入abcde34时,会输出34
当输入aA34时,会输出34
cin.fail()
cin.fail判断流操作是否失败.如果输入失败就会返回true.
所以可以与while函数搭配使用,例如
int a;
cin>>a;
if(cin.fail())
{
cout<<"请输入整数"<<endl;
}
else
{
//你希望执行的代码部分
}
cin.clear(); //使流重新处于有效状态
cin.sync(); //清除缓存区的数据流
cin.sync() 表示清除缓存区的数据流。必须 cin.clear() 在前,cin.sync() 在后。因为在流中 fail() 状态值无效的情况下,执行cin.sync() 清空流是无效的,输入流中的数据依旧在(从错误开始那个,包括错误那个字符仍然在流中)。
当我们输入英文字母’k’时,它的状态标识改为fail,即错误,用cout对用户输出信息,再用cin.clear让错误标识改回为0,让我们可以继续输入,再清空流数据继续输入.如果我们没有了cin.clear,则会进入死循环,其过程为我们输入了英文字母,它的状态标识便为fail,当运行到条件判断时,便总是回到错误的条件表示里,并且我们再也没办法输入,因为错误的表示关闭了cin,所以会进入死循环.
注:cin.sync();在不同的编译器下实现的情况可能有所不同,从而导致问题无法解决,所以还是推荐使用cin.ignore()