有没有可以做各种字体的网站,网站编辑做seo好做吗,制作自己的app多少钱,网站的备案可以管几年在之前的博客中已经讲过了C语言中的结构体概念了#xff0c;重复的内容在这儿就不赘述了。C中的结构体在C语言的基础上还有些补充#xff0c;在这里说明一下#xff0c;顺便简单地讲一下类的概念。
一、成员函数 结构体类型声明的关键字是 struct #xff0c;在C中结构体…在之前的博客中已经讲过了C语言中的结构体概念了重复的内容在这儿就不赘述了。C中的结构体在C语言的基础上还有些补充在这里说明一下顺便简单地讲一下类的概念。
一、成员函数 结构体类型声明的关键字是 struct 在C中结构体类型声明的基本语法如下 struct tag
{成员变量列表; //成员变量可以有1个也可以有多个成员函数列表; //成员函数可以有也可以没有
} 结构体变量列表; //在声明结构体类型的同时创建结构体变量可以有多个中间使⽤逗号隔开 我们可以发现C中的结构体和C语言结构体的有一个比较大的差异就是C中的结构体中除了有成员变量之外还可以包含成员函数。下面先概要地介绍一下成员函数 1C的结构体会有一些默认的成员函数比如构造函数、析构函数等是编译器默认生成的如果觉得不合适也是可以自己显示的定义这些函数这些函数都是自动被调用不需要手动调用。 2除了默认的成员函数之外我们可以自己定义一些成员函数这些成员函数可以有也可以没有完全根据的实际的需要来添加就可以。 3这些成员函数可以直接访问成员变量。 4成员函数的调用也使用 . 操作符。 1. 构造函数 构造函数是结构中默认的成员函数之一构造函数的主要的任务是初始化结构体变量。写了构造函 数就不需要再写其他成员函数来初始化结构体(类)的成员而且构造函数是在结构变量创建的时候编译器自动被调用的。 构造函数的特征如下 1函数名与结构体(类)名相同。 2无返回值。 3构造函数可以重载。 4若未显式定义构造函数系统会自动生成默认的构造函数。 2. 析构函数 析构函数是用来完成结构体变量中资源的清理工作也是结构体中默认的成员函数之一。析构函数在结构体变量销毁的时候被自动调用的。 析构函数的特征如下 1析构函数名是在结构体(类)名前加上字符 ~ 。 2无参数无返回值类型。 3一个类只能有一个析构函数。若未显式定义析构函数系统会自动生成默认的析构函数。注意析构函数不能重载。 #include iostream
using namespace std;
struct Stu
{//成员变量string name;int chinese;int math;int total; //构造函数Stu(){cout 调用构造函数 endl;name 小明;chinese 99;math 95;total math chinese;}//析构函数~Stu(){cout 调用析构函数 endl;//对于当前这个类的对象没有啥资源清理}
};
int main()
{struct Stu s;return 0;
} 运行结果打印了调用构造函数和调用析构函数这两句话这也验证了构造函数和析构函数是会被自动调用的。 3.自定义函数 创建结构体中的自定义函数和我们平时创建自定义函数的方式是一样的只是在使用的时候需要使用 . 操作符。 #include iostream
using namespace std;
struct Stu
{//成员变量string name;int chinese;int math;int total;//构造函数Stu(){name 小明;chinese 99;math 95;total math chinese;}void print_stu() //打印{cout 名字: name endl;cout 语文: chinese endl;cout 数学: math endl;cout 总分: total endl;}
};
int main()
{struct Stu s;s.print_stu();return 0;
} 二、运算符重载 我们在C中打印数据的时候习惯了直接使用 cout 来直接打印数据的。比如 int n 100;
float f 3.14f;
cout n endl;
cout f endl; 那针对 struct Stu 类型的变量能不能直接使用 cout 来打印呢当我们直接使用时会发现这样是行不通的。 那怎么解决呢其实在C中要针对自定义类型的变量想使用 cout 和 来输出变量的内容 就得对 这个输出运算符进行重载。具体代码如下 #include iostream
using namespace std;
struct Stu
{//成员变量string name;int chinese;int math;int total;
};
//重载输出运算符
ostream operator(ostream os, const Stu s)
{os 名字: s.name endl;os 语文: s.chinese endl;os 数学: s.math endl;os 总分: s.total endl;return os;
}
int main()
{struct Stu s {张三, 90, 80, 170};cout s endl; return 0;
} ostream表示该函数返回一个指向 ostream 对象的引用。ostream 是C中用于输出流的标准库类例如 cout 就是 ostream 类型的一个实例。 operator这是重载运算符的语法允许你定义当使用 运算符时应该执行的操作。这里我们重载了 运算符使其能够接受 ostream 和 Stu 类型的参数并按特定格式输出对象的信息。 (ostream os, const Stu s)这个函数接受两个参数第一个是 ostream 类型的引用 os代表输出流如 cout第二个是一个常量引用 const Stu s即要输出的 Stu 类型对象。 接下来就简单地讲集几种运算符重载。 1.加号运算符重载 #include iostream
using namespace std;
struct Stu
{int a;float b;Stu operator(Stu s){Stu s3;s3.aas.a;return s3;}
}s1,s2;
int main()
{s1.a1;s2.a2;Stu s3s1s2;cout s3.a;return 0;
} 在这段代码中Stu operator(Stu s) 是一个成员函数用于重载加法运算符以便两个 Stu 类型的对象可以相加。它接受一个 Stu 类型的参数 s 并返回一个 Stu 类型的结果。由于这是一个成员函数它隐式地接收调用它的对象作为第一个参数。这个运算符重载为s1.operator(s2)可以简化为s1s2。当然我们也可以使用全局函数的方式来实现运算符的重载。 #include iostream
using namespace std;
struct Stu
{int a;float b;
}s1,s2;
Stu operator(Stu s1,Stu s2)
{Stu s3;s3.as1.as2.a;return s3;
}
int main()
{s1.a1;s2.a2;Stu s3s1s2;cout s3.a;return 0;
} 这个运算符重载为operator(s1,s2)可以简化为s1s2。 2.左移运算符重载 最上面举的cout的例子就是左移运算符重载是采取全局函数的方式来实现的。在这里顺便一提在这里如果我们使用成员函数的方式是实现不了的在下面代码中我们可以看出虽然能够重载这个运算符但是实现的效果为s cout 并不是我们想要的结果。 #include iostream
using namespace std;
struct Stu
{//成员变量string name;int chinese;int math;int total;//重载输出运算符
ostream operator(ostream os)
{os 名字: name endl;os 语文: chinese endl;os 数学: math endl;os 总分: total endl;return os;
}
};
int main()
{struct Stu s {张三, 90, 80, 170};s cout; return 0;
} 3.递增运算符重载 #include iostream
using namespace std;
struct Stu
{int a;//前置重载 Stu operator(){a;return *this;}//后置重载Stu operator(int){Stu s*this;a;return s;}
}s;//重载输出运算符
ostream operator(ostream os,const Stu s)
{os s.a endl;return os;
}
void test1()
{cout s;
}
void test2()
{cout s;
}
int main()
{s.a1;test1();s.a1;test2();return 0;
} 在自增运算符的重载中许多思想是和之前一样的区别在于前置运算符重载作为成员函数时没有额外参数后置运算符重载作为成员函数时需要一个额外的、类型为int的占位参数。这个参数通常不使用只是用来与前置运算符区分开来。还有一个注意的点是在前置重载时我们把返回值的类型设为了结构体的引用这是因为当我们对内置数据连续自增操作是对该数据连续自增的说起来很奇怪其实就是进行一次自增操作变量就自增一次。但如果在这里我们不使用引用就会返回一个结构体类型的临时变量如果在进行自增操作对于原来的结构体变量是没有影响的。而后置是不会进行连续操作的所以我们不需要考虑。 4.关系运算符重载 #include iostream
#include string
using namespace std;
struct Stu
{string name;int age;bool operator(Stu s){if(this-names.namethis-ages.age)return true;elsereturn false;}
};
int main()
{Stu s1{Tom,12};Stu s2{Tom,12};if(s1s2)cout same endl;return 0;
} 三、结构体排序 - sort 说到排序我们之前讲过冒泡排序我们也可以写一个冒泡排序函数来排序一组结构体数据但是这里给大家介绍一个 C 的 STL 中的库函数 sort 可以直接用来排序数据只要涉及到数据的排序又没有明确要求自己实现排序算法的时候就可以直接使用sort函数。 1.sort 函数介绍 函数原型如下 //版本1
template class RandomAccessIterator
void sort (RandomAccessIterator first, RandomAccessIterator last);
//void sort(开始位置结束位置);
//first指向要排序范围的第⼀个元素的迭代器或者指针。
//last指向要排序范围的最后⼀个元素之后位置的迭代器或者指针。
//版本2
template class RandomAccessIterator, class Compare
void sort (RandomAccessIterator first, RandomAccessIterator last, Compare
comp);
//void sort(开始位置结束位置⾃定义排序函数);
//first指向要排序范围的第⼀个元素的迭代器或者指针。
//last指向要排序范围的最后⼀个元素之后位置的迭代器或者指针。
//comp是⼀个⽐较函数或者函数对象
//这⾥开始位置和结束位置可以是指针也可以是迭代器
//⾃定义排序函数 可以是函数也可以是仿函数 sort 函数需要包含的头文件 algorithm。在默认情况下 sort 函数按升序对给定范围 [firstlast中的元素进行排序。 2.排序内置类型数据 对数组进行排序 #include iostream
#include algorithm
using namespace std;
int main()
{int arr[] { 4,5,6,9,7,1,2,8,5,4,2 };int size sizeof(arr) / sizeof(arr[0]);//起始位置和结束位置传的是地址sort(arr, arr size);for (int i 0; i size; i){cout arr[i] ;}cout endl;return 0;
} 默认排序结果是升序的。 对字符串中的字符进行排序 #include iostream
#include algorithm
#include string
using namespace std;
int main()
{string s(defxxxabccba);sort(s.begin(), s.end());cout s endl;return 0;
} 这里是对字符串中字符的顺序进行排序是按照字符的ASCII值进行排序的。默认排序的结果依然是升序。 3.自定义排序 sort 在默认的情况下是按照升序排序如何按照降序排序呢如果是结构体类型数据进行排序呢 怎么办我们可以使用自定义排序方式 void sort (RandomAccessIterator first, RandomAccessIterator last, Compare
comp); sort 的第三个参数是一个可选的自定义比较函数或函数对象用于指定排序的规则。如果不提 供这个参数 std::sort 默认会使用小于运算符 ( ) 来比较元素并按照升序排序。这个比较函数接受两个参数并返回一个布尔值。如果第一个参数应该排在第二个参数之前则返回 true否则返回 false。 接下来试试看comp 表示可以自定义一个排序方法使用方法如下 #include iostream
#include algorithm
using namespace std;
//自定义一个比较函数这个⽐较函数能够⽐较被排序数据的2个元素大小
//函数返回bool类型的值
bool compare(int x, int y)
{return x y;//排降序
}
int main()
{int arr[] { 4,5,6,9,7,1,2,8,5,4,2 };int size sizeof(arr) / sizeof(arr[0]);//将函数名作为第三个参数传⼊sort函数中sort(arr, arr size, compare);for (int i 0; i size; i){cout arr[i] ;}cout endl;return 0;
} 当然第三个参数还可以使用结构体中重载()运算符-仿函数。 #include iostream
#includealgorithm
using namespace std;
//仿函数⽅式 - 仿函数也叫函数对象
struct Cmp
{bool operator()(int x, int y){return x y;//排降序}
}cmp;
int main()
{int arr[] { 4,5,6,9,7,1,2,8,5,4,2 };int size sizeof(arr) / sizeof(arr[0]);//将结构体对象作为第三个参数传⼊sort函数中sort(arr, arr size, cmp);for (int i 0; i size; i){cout arr[i] ;}cout endl;return 0;
} 四、类 C中为了更好的实现面向对象更喜欢使用 class (类)来替换 struct (结构体)。你可以简单粗暴 的理解为 class 和 struct 是一回事但是其实本上还是有区别的。 1. 类定义 类的关键字是 class 类中主要也是由两部分组成分别为成员变量和成员函数。形式如下 class tag
{
public:成员变量列表;成员函数列表;
}; // ⼀定要注意后⾯的分号 class 是用来定义类类型的关键字在类中可以定义成员函数和成员变量。 public 是类成员权限访问限定符标志类中的成员可以公开访问及调用。 在这里我们就能发现一个与结构体不同的地方结构体中没有public。这是为什么呢 原因是结构体的成员变量和成员函数默认就是公开的而 class 中的成员变量和成员 函数默认是私有的 private 。 class Stu
{
public: void init_stu() {name ⼩明;chinese 0;math 0;total 0;}string name; //名字int chinese; //语⽂成绩int math; //数学成绩int total; //总成绩
}; 2.类的使用 1 创建类对象 int main()
{Stu s1; //创建类对象s1Stu s2; //创建类对象s2return 0;
} 2调用类对象成员 像结构体一样通过操作符 . 即可对类对象的成员进行访问。 #include iostream
using namespace std;
int main()
{//创建类对象Stu s1;//调⽤成员变量s1.name 张三;s1.chinese 90;s1.math 98;s1.total s1.chinese s1.math;Stu s2;//调⽤成员函数s2.init_stu();return 0;
} 3.访问权限控制 访问限定符是C语言中的关键字用于指定类成员的访问权限。 访问限定符主要有三个 public 成员被声明为 public 后可以被该类的任何方法访问包括在类的外部。 protected 成员被声明为 protected 后可以被该类访问。 private 成员被声明为 private 后只能被该类的成员函数访问。 #include iostream
using namespace std;class Stu
{
public: //将成员函数设置为公有属性void init_stu() {name ⼩明;chinese 0;math 0;total 0;}
private: //将成员变量设置为私有属性string name; //名字int chinese; //语⽂成绩int math; //数学成绩int total; //总成绩
};
int main()
{Stu stu;stu.init_stu(); //访问公有成员函数cout stu.name endl; //访问私有成员变量编译器报错return 0;
} 通过运行结果可见类外可直接访问设置为公有的成员而不可以直接访问私有的成员。 习惯上外部可访问的成员函数通常设置为公有属性 public 而为了提高成员变量的 访问安全性通常将成员变量设置为私有属性 private 即只有类内部可以访问。 4.结构体和类的区别 C中 struct 和 class 的区别是什么 C兼容了C语言所以C中 struct 既可以当成结构体使用还可以用来定义类和 class 定义 类是一样的。区别是 struct 定义的类默认访问权限是 public class 定义的类默认访问权限是 private 。 类的定义既可以使用 struct 也可以使用 class。C更常用 class 关键词来定义类因此在选用 class 的时候需要加上访问限定符 public 才可以在类外调用类的成员函数和成员变量。