当前位置: 首页 > news >正文

C++【个人笔记1】

1.C++的初识

1.1 简单入门

#include<iostream>
using namespace std;
int main() {cout << "hello world" << endl;return 0;
}
  1. #include<iostream>; 预编译指令,引入头文件iostream.
  2. using namespace std; 使用标准命名空间
  3. cout << “hello world”<< endl; 和printf功能一样,输出字符串”hello wrold”

问题1:c++头文件为什么没有.h?

在c语言中头文件使用扩展名.h,将其作为一种通过名称标识文件类型的简单方式。但是c++得用法改变了,c++头文件没有扩展名。但是有些c语言的头文件被转换为c++的头文件,这些文件被重新命名,丢掉了扩展名.h(使之成为c++风格头文件),并在文件名称前面加上前缀c(表明来自c语言)。例如c++版本的math.h为cmath.

问题2:using namespace std 是什么?

namespace是指标识符的各种可见范围。命名空间用关键字namespace 来定义。命名空间是C++的一种机制,用来把单个标识符下的大量有逻辑联系的程序实体组合到一起。此标识符作为此组群的名字。

问题3:cout 、endl 是什么?

cout是c++中的标准输出流,endl是输出换行并刷新缓冲区。

1.2 namespace 【命名空间】

C++中自定义命名空间(namespace)及其使用的三种方法_自定义namespace-CSDN博客

由于namespace的概念,使用C++标准程序库的任何标识符时,可 以有三种选择:

1)直接指定标识符。例如std::ostream而不是ostream。完整语句如 下:

std::cout	<<	std::hex	<<	3.4	<<	std::endl;	

2)使用using关键字。

using	std::cout;	
using	std::endl;	
using	std::cin;

3)最方便的就是使用using namespace std;

4.命名空间使用语法

  1. 创建一个命名空间:
namespace A{int a = 10;
}
namespace B{int a = 20;
}
void test(){cout << "A::a : " << A::a << endl;cout << "B::a : " << B::a << endl;
}

        2.命名空间只能全局范围内定义(以下错误写法)

void test(){namespace A{int a = 10;}namespace B{int a = 20;}cout << "A::a : " << A::a << endl;cout << "B::a : " << B::a << endl;
}

        3.命名空间可以嵌套命名

namespace A{int a = 10;namespace B{int a = 20;}
}
void test(){cout << "A::a : " << A::a << endl;cout << "A::B::a : " << A::B::a << endl;
}

        4.命名空间是开放的,可以随时加入新的成员

namespace A{int a = 10;
}namespace A{void func(){cout << "hello namespace!" << endl;}
}

        5.声明和实现可以分离

#pragma oncenamespace MySpace{void func1();void func2(int param);
}void MySpace::func1(){cout << "MySpace::func1" << endl;
}
void MySpace::func2(int param){cout << "MySpace::func2 : " << param << endl;
}

        6.命名空间起别名

namespace veryLongName{int a = 10;void func(){ cout << "hello namespace" << endl; }
}void test(){namespace shortName = veryLongName;cout << "veryLongName::a : " << shortName::a << endl;veryLongName::func();shortName::func();
}

2.C++对C的扩展

2.1 ::作用域运算符

#define _CRT_SECURE_NO_WARNINGS
#include <iostream>using namespace std;//定义一个命名空间
namespace spaccA {int g_a = 10;
}namespace spaceB {int a = 20;namespace spaceC {struct teacher{int id;char name[64];};}namespace spaceD {struct teacher{int id;char name[64];};}using namespace spaceC;}int main(void)
{//using spaccA::g_a;using namespace spaccA;int a = 10;cout << g_a << endl;//spaceB::spaceC::teacher t1;//using spaceB::spaceC::teacher;//teacher t1;//using namespace spaceB::spaceC;//spaceB::spaceC::teacher t1;using namespace spaceB;teacher t1;t1.id = 10;//spaceB::spaceD::teacher t2;//t2.id = 20;return 0;
}

2.2 "实用性“增强

c语言一定要在使用之前先定义

c++可以在使用的时候进行定义

//C语⾔中的变量都必须在作⽤域开始的位置定义!!
//C++中更强调语⾔的“实⽤性”,所有的变量都可以在需要使⽤时再定义。
#include<iostream>
using namespace std;
int main() {int i = 0;cout << "i=" << i << endl;int k = 4;cout << "k=" << k << endl;return 0;
}

2.3 变量检测增强

c语言允许定义多个同名的变量

c++不能定义多个同名变量,即使作用域不同

/*在C语⾔中,重复定义多个同名的全局变量是合法的在C++中,不允许定义多个同名的全局变量C语⾔中多个同名的全局变量最终会被链接到全局数据区的同⼀个地址空间上int	g_var;int	g_var	=	1;C++直接拒绝这种⼆义性的做法。
*/
#include<iostream>
int	g_var;
int	g_var = 1;
int	main(int argc, char* argv[])
{printf("g_var	=	%d\n", g_var);return 0;
}

2.4 C++中所有变量和函数都必须有类型

C++中所有的变量和函数都必须有类型

C语⾔中的默认类型在C++中是不合法的

函数f的返回值是什么类型,参数⼜是什么类型?

函数g可以接受多少个参数?

//i没有写类型,可以是任意类型
int fun1(i){printf("%d\n", i);return 0;
}
//i没有写类型,可以是任意类型
int fun2(i){printf("%s\n", i);return 0;
}
//没有写参数,代表可以传任何类型的实参
int fun3(){ printf("fun33333333333333333\n");return 0;
}//C语言,如果函数没有参数,建议写void,代表没有参数
int fun4(void){printf("fun4444444444444\n");return 0;
}g(){return 10;
}int main(){fun1(10);fun2("abc");fun3(1, 2, "abc");printf("g = %d\n", g());return 0;
}
  1. 在C语言中,int fun() 表示返回值为int,接受任意参数的函数,int fun(void) 表示返回值为int的无参函数。
  2. 在C++ 中,int fun() 和int fun(void) 具有相同的意义,都表示返回值为int的无参函数。

2.5 更严格的类型转换

在C++,不同类型的变量一般是不能直接赋值的,需要相应的强转。

以上c代码c编译器编译可通过,c++编译器无法编译通过。

typedef enum COLOR{ GREEN, RED, YELLOW } color;
int main(){color mycolor = GREEN;mycolor = 10;printf("mycolor:%d\n", mycolor);char* p = malloc(10);return EXIT_SUCCESS;
}

2.6 struct类型加强

  1. c中定义结构体变量需要加上struct关键字,c++不需要。
  2. c中的结构体只能定义成员变量,不能定义成员函数。c++即可以定义成员变量,也可以定义成员函数。
//1. 结构体中即可以定义成员变量,也可以定义成员函数
struct Student{string mName;int mAge;void setName(string name){ mName = name; }void setAge(int age){ mAge = age; }void showStudent(){cout << "Name:" << mName << " Age:" << mAge << endl;}
};//2. c++中定义结构体变量不需要加struct关键字
void test01(){Student student;student.setName("John");student.setAge(20);student.showStudent();
}

2.7 对函数返回参数个数的要求

C传递参数大于实际定义的参数,只会报警告,C++传递参数大于实际定义的参数会报错

2.8 新增的bool类的关键字

bool b=100;//无论将修改为多少,sizeof(b)永远为1

#include	<iostream>
using namespace	std;
int	main(int	argc, char* argv[])
{int	a;bool	b = true;printf("b	=	%d,	sizeof(b)	=	%d\n", b, sizeof(b));//1   1b = 4;a = b;printf("a	=	%d,	b	=	%d\n", a, b);//1   1b = -4;a = b;printf("a	=	%d,	b	=	%d\n", a, b);//1     1a = 10;b = a;printf("a	=	%d,	b	=	%d\n", a, b);//10   1b = 0;printf("b	=	%d\n", b);//0return 0;
}

2.9 三目运算符功能增强

  1. c语言三目运算表达式返回值为数据值,为右值,不能赋值。
	int a = 10;int b = 20;printf("ret:%d\n", a > b ? a : b);//思考一个问题,(a > b ? a : b) 三目运算表达式返回的是什么?//(a > b ? a : b) = 100;//错误//返回的是右值
  1. c++语言三目运算表达式返回值为变量本身(引用),为左值,可以赋值。
int a = 10;int b = 20;printf("ret:%d\n", a > b ? a : b);//思考一个问题,(a > b ? a : b) 三目运算表达式返回的是什么?cout << "b:" << b << endl;//20//返回的是左值,变量的引用(a > b ? a : b) = 100;//返回的是左值,变量的引用cout << "b:" << b << endl;//100

2.10 const增强

const单词字面意思为常数,不变的。它是c/c++中的一个关键字,是一个限定符,它用来限定一个变量不允许改变,它将一个对象转换成一个常量。

1.c语言中的const

们c中的const理解为”一个不能改变的普通变量”,也就是认为const应该是一个只读变量,既然是变量那么就会给const分配内存,并且在c中const是一个全局只读变量,c语言中const修饰的只读变量是外部连接的。

2.c++中的const

在c++中,一个const不必创建内存空间,而在c中,一个const总是需要一块内存空间。在c++中,是否为const常量分配内存空间依赖于如何使用。一般说来,如果一个const仅仅用来把一个名字用一个值代替(就像使用#define一样),那么该存储局空间就不必创建。

3.C/C++中const异同总结

//const	定义常量--->	const	意味只读
const int	a;	
int const	b;	
//第⼀个第⼆个意思⼀样 代表⼀个常整形数
const int	*c;	
//第三个	c是⼀个指向常整形数的指针(所指向的内存数据不能被修改,但是本⾝可以修改)
int	*	const	d;	
//第四个	d	常指针(指针变量不能被修改,但是它所指向内存空间可以被修改)
const int	*	const	e	;	
//第五个	e⼀个指向常整形的常指针(指针和它所指向的内存空间,均不能被修改)

4.const 和 #define 的相同

#include	<iostream>		
//#define	N	10	
int	main()	
{	const int	a	=	1;			const int	b	=	2;			int	array[a	+	b]	=	{0};	int	i	=	0;							for(i	=	0;	i	<	(a+b);	i++)	{																												printf("array[%d]	=	%d\n",	i,	array[i]);	}																																												return 0;																				
}

C++中的const修饰的,是一个真正的常量,而不是C中变量(只读)。在 const修饰的常量编译期间,就已经确定下来了

5.const 和 #define 的区别

#include	<iostream>
void	fun1()	
{	#define	a	10const int	b	=	20;	
}	
void	fun2()	
{	printf("a	=	%d\n",	a);	//printf("b	=	%d\n",	b);
}	
int	main()	
{	fun1();	fun2();	return 0;	
}

  1. const有类型,可进行编译器类型安全检查。#define无类型,不可进行类型检查.
  2. const有作用域,而#define不重视作用域,默认定义处到文件结尾.如果定义在指定作用域下有效的常量,那么#define就不能用。

辨析;
 

#include	<stdio.h>
int	main()
{const int	a = 10;//将a的地址传递给pint* p = (int*)&a;printf("a===>%d\n", a);//10*p = 11;printf("a===>%d\n", a);//10return 0;
}
#include	<iostream>		
//#define	N	10	
int	main()
{const int	a = 1;const int	b = 2;int	array[a + b] = { 0 };int	i = 0;for (i = 0; i < (a + b); i++){printf("array[%d]	=	%d\n", i, array[i]);//0 0 0}return 0;
}
#include	<iostream>
void	fun1()
{
#define	a	10const int	b = 20;
}
void	fun2()
{printf("a	=	%d\n", a);//10//printf("b	=	%d\n",	b);
}
int	main()
{fun1();fun2();return 0;
}

2.11 真正的枚举

c 语言中枚举本质就是整型,枚举变量可以用任意整型赋值。而 c++中枚举 变量, 只能用被枚举出来的元素初始化。

#include<iostream>
using namespace	std;	
enum season	{SPR,SUM,AUT,WIN};	
int	main()	
{	enum	season	s	=	SPR;	//s	=	0;	//	error,	但是C语⾔可以通过s	=	SUM;	cout	<<	"s	=	"	<<	s	<<endl;//1return 0;	
}

3 引⽤(reference)

3.1 引用基本用法

引用是c++对c的重要扩充。在c/c++中指针的作用基本都是一样的,但是c++增加了另外一种给函数传递地址的途径,这就是按引用传递(pass-by-reference),它也存在于其他一些编程语言中,并不是c++的发明。

  1. 变量名实质上是一段连续内存空间的别名,是一个标号(门牌号)
  2. 程序中通过变量来申请并命名内存空间
  3. 通过变量的名字可以使用存储空间

对一段连续的内存空间只能取一个别名吗?

c++中新增了引用的概念,引用可以作为一个已定义变量的别名。

基本语法

Type & ref=val;
int & ref=&a;//表示ref是a的别名
#include<iostream>
using namespace std;
int main() {int a = 10;int& b = a;//int* ba = 11;{int* p = &a;*p = 12;cout << a << endl;//12}b = 14;cout << a <<"" << b << endl;//14 14
}

注意事项:

  1. &在此不是求地址运算,而是起标识作用。
  2. 类型标识符是指目标变量的类型
  1. 必须在声明引用变量时进行初始化。
  2. 引用初始化之后不能改变。
  3. 不能有NULL引用。必须确保引用是和一块合法的存储单元关联。
  4. 可以建立对数组的引用。
//1. 认识引用
void test01(){int a = 10;//给变量a取一个别名bint& b = a;cout << "a:" << a << endl;cout << "b:" << b << endl;cout << "------------" << endl;//操作b就相当于操作a本身b = 100;cout << "a:" << a << endl;cout << "b:" << b << endl;cout << "------------" << endl;//一个变量可以有n个别名int& c = a;//给c取了一个名为”c”的别名c = 200;cout << "a:" << a << endl;cout << "b:" << b << endl;cout << "c:" << c << endl;cout << "------------" << endl;//a,b,c的地址都是相同的cout << "a:" << &a << endl;cout << "b:" << &b << endl;cout << "c:" << &c << endl;
}
//2. 使用引用注意事项
void test02(){//1) 引用必须初始化//int& ref; //报错:必须初始化引用//2) 引用一旦初始化,不能改变引用int a = 10;int b = 20;int& ref = a;ref = b; //不能改变引用//3) 不能对数组建立引用int arr[10];//int& ref3[10] = arr;
}

3.2 注意点 

1.一个变量可以有n个别名

2.操作别名等于操作原数

3.别名和操作数的地址是一样的

4.引用必须初始化

5.一旦初始化,不能进行修改

6.不能对数组建立引用

3.3 建立对数组的引用

方法一:

	typedef int ArrRef[10];int arr[10];ArrRef& aRef = arr;for (int i = 0; i < 10;i ++){aRef[i] = i+1;}for (int i = 0; i < 10;i++){cout << arr[i] << " ";}cout << endl;

方法二:

	int(&f)[10] = arr;for (int i = 0; i < 10; i++){f[i] = i+10;}for (int i = 0; i < 10; i++){cout << arr[i] << " ";}cout << endl;

3.4 函数中的引用

当引用被用作函数参数的时,在函数内对任何引用的修改,将对还函数外的参数产生改变

//值传递
void ValueSwap(int m,int n){int temp = m;m = n;n = temp;
}
//地址传递
void PointerSwap(int* m,int* n){int temp = *m;*m = *n;*n = temp;
}
//引用传递
void ReferenceSwap(int& m,int& n){int temp = m;m = n;n = temp;
}
void test(){int a = 10;int b = 20;//值传递ValueSwap(a, b);cout << "a:" << a << " b:" << b << endl;//地址传递PointerSwap(&a, &b);cout << "a:" << a << " b:" << b << endl;//引用传递ReferenceSwap(a, b);cout << "a:" << a << " b:" << b << endl;
}

通过引用参数产生的效果同按地址传递是一样的。引用的语法更清楚简单:  

  1. 函数调用时传递的实参不必加“&”符
  2. 在被调函数中不必在参数前加“*”符

引用作为其它变量的别名而存在,因此在一些场合可以代替指针。C++主张用引用传递取代地址传递的方式,因为引用语法容易且不易出错。

#include	<iostream>
using namespace	std;
int	getA1()
{int	a;a = 10;return	a;
}
int& getA2()
{int	a;a = 10;return	a;
}
int	main(void)
{int	a1 = 0;int	a2 = 0;//值拷⻉a1 = getA1();//将⼀个引⽤赋给⼀个变量,会有拷⻉动作//理解: 编译器类似做了如下隐藏操作,a2	=	*(getA2())a2 = getA2();//将⼀个引⽤赋给另⼀个引⽤作为初始值,由于是栈的引⽤,内存⾮法int& a3 = getA2();cout << "a1	=	" << a1 << endl;cout << "a2	=	" << a2 << endl;cout << "a3	=	" << a3 << endl;return 0;
}
#include	<iostream>
using namespace	std;
//函数当左值
//返回变量的值
int	func1()
{static int	a1 = 10;return	a1;
}
//返回变量本⾝	,	
int& func2()
{static int	a2 = 10;return	a2;
}
int	main(void)
{//函数当右值int	c1 = func1();cout << "c1	=	" << c1 << endl;int	c2 = func2();	//函数返回值是⼀个引⽤,并且当右值cout << "c2	=	" << c2 << endl;//函数当左值//func1()	=	100;				//errorfunc2() = 100;						//函数返回值是⼀个引⽤,并且当左值c2 = func2();cout << "c2	=	" << c2 << endl;return 0;
}

注意点:

  1. 不能返回局部变量的引用。
  2. 函数当左值,必须返回引用。【因为引用定义的函数,返回的是别名】

3.5 引用的本质:指针常量.(int* const ref)

引用的本质在c++内部实现是一个指针常量.

Type& ref = val; // Type* const ref = &val;

c++编译器在编译过程中使用常指针作为引用的内部实现,因此引用所占用的空间大小与指针相同,只是这个过程是编译器内部实现,用户不可见。

//发现是引用,转换为 int* const ref = &a;
void testFunc(int& ref){ref = 100; // ref是引用,转换为*ref = 100
}
int main(){int a = 10;int& aRef = a; //自动转换为 int* const aRef = &a;这也能说明引用为什么必须初始化aRef = 20; //内部发现aRef是引用,自动帮我们转换为: *aRef = 20;cout << "a:" << a << endl;cout << "aRef:" << aRef << endl;testFunc(a);return EXIT_SUCCESS;
}

3.6 指针引用

对于c++中的定义那个,语法清晰多了。函数参数变成指针的引用,用不着取得指针的地址。

struct Teacher{int mAge;
};
//指针间接修改teacher的年龄
void AllocateAndInitByPointer(Teacher** teacher){*teacher = (Teacher*)malloc(sizeof(Teacher));(*teacher)->mAge = 200;  
}
//引用修改teacher年龄
void AllocateAndInitByReference(Teacher*& teacher){teacher->mAge = 300;
}
void test(){//创建TeacherTeacher* teacher = NULL;//指针间接赋值AllocateAndInitByPointer(&teacher);cout << "AllocateAndInitByPointer:" << teacher->mAge << endl;//引用赋值,将teacher本身传到ChangeAgeByReference函数中AllocateAndInitByReference(teacher);cout << "AllocateAndInitByReference:" << teacher->mAge << endl;free(teacher);
}
#include	<iostream>
using namespace	std;
struct	Teacher
{char	name[64];int	age;
};
//在被调⽤函数 获取资源
int	getTeacher(Teacher * *p)
{Teacher* tmp = NULL;if (p == NULL){return	-1;}tmp = (Teacher*)malloc(sizeof(Teacher));if (tmp == NULL){return	-2;}tmp->age = 33;//	p是实参的地址		*实参的地址 去间接的修改实参的值*p = tmp;return 0;
}
//指针的引⽤ 做函数参数
int	getTeacher2(Teacher*& myp)
{//给myp赋值 相当于给main函数中的pT1赋值myp = (Teacher*)malloc(sizeof(Teacher));if (myp == NULL){return	-1;}myp->age = 36;return 0;
}
void	FreeTeacher(Teacher* pT1)
{if (pT1 == NULL){return;}free(pT1);
}
int	main(void)
{Teacher* pT1 = NULL;//1	c语⾔中的⼆级指针getTeacher(&pT1);cout << "age:" << pT1->age << endl;FreeTeacher(pT1);//2	c++中的引⽤ (指针的引⽤)//引⽤的本质 间接赋值后2个条件 让c++编译器帮我们程序员做了。getTeacher2(pT1);cout << "age:" << pT1->age << endl;FreeTeacher(pT1);return 0;
}

3.7 常量引用(const)

常量引用的定义格式:

const Type& ref = val;

注意:

  1. 如果想对一个常量进行引用, 必须是一个const引用。
  2. const修饰的引用,不能修改。

void test01(){int a = 100;const int& aRef = a; //此时aRef就是a//aRef = 200; 不能通过aRef的值a = 120; //OKcout << "a:" << a << endl;//120cout << "aRef:" << aRef << endl;//120
}
void test02(){//不能把一个字面量赋给引用//int& ref = 100;//但是可以把一个字面量赋给常引用//因为const int的级别比int高const int& ref = 100; //int temp = 200; const int& ret = temp;
}

    [const引用使用场景]

    常量引用主要用在函数的形参,尤其是类的拷贝/复制构造函数。

将函数的形参定义为常量引用的好处:

  • 引用不产生新的变量,减少形参与实参传递时的开销。
  • 由于引用可能导致实参随形参改变而改变,将其定义为常量引用可以消除这种副作用。

    如果希望实参随着形参的改变而改变,那么使用一般的引用,如果不希望实参随着形参改变,那么使用常引用。

//const int& param防止函数中意外修改数据
void ShowVal(const int& param){cout << "param:" << param << endl;
}

3.8 例子

C++引用10分钟入门教程

#include	<iostream>
using namespace	std;
int	main(void)
{int	a = 10;	//c编译器分配4个字节内存,	a内存空间的别名int& b = a;		//b就是a的别名-->const * int b=aa = 11;	//直接赋值{int* p = &a;*p = 12;cout << a << endl;//12}b = 14;cout << "a	=	" << a << ",	b	=	" << b << endl;//14 14return 0;
}

结论:可以通过普通参数修改引用,但是不能通过引用修改参数 

#include	<iostream>
using namespace	std;
int main() {int a = 20;int&  ref = a;ref = 30;cout << ref << a << endl;//30  30int b = 40;const int& ref2 = b;b = 100;cout << ref2 << b << endl;//100 100int& rref = ref;rref = 200;cout << rref << ref << a << endl;//200 200 200
}

作业:

1.简述C++中命名空间的作用。

namespace AAA{
    int a;

using AAA::a;
AAA::a;
using namespace AAA;

2. 定义两个命名空间A 和 B 分别在A中和B中定义变量value

#include<iostream>using namespace std;namespace A {int a = 10;
}
namespace B {int b = 20;
}
int main() {using namespace A;using namespace B;cout << A::a << endl;cout << B::b << endl;}

3. C语言的三目运算符 ? : , 可以当左值么? C++的是否可以? 为什么?

c语言的三目运算符不可以当左值,因为返回的是一个常量。

c++的三目运算符可以做左值

4. 下面哪条语句是错误的?为什么?

(1 < 2? a: b) = 100;//正确,因为结果是一个变量,可以被赋值
   
(1 < 2? 10: 20) = 100//错误,因为结果是一个常量,常量不能被常量赋值

5. const int a; 在C++编译器中是否需要初始化,为什么?
 

在c++中,一旦声明一个const变量,则在声明的过程中一定要对起进行初始化

6.temp

int main() {int a = 10;int* p = (int*)&a;//*p:实际上修改的是temp的值*p = 20;cout << a << endl;//20cout << *p << endl;//20}

6. 简述引用的特点?

1.引用本身不占用内存空间,与被引用对象共用内存

2.引用定义时,必须初始化

3.引用的类型必须与被引用对象的类型保持一致 比如:int a; 引用必须使用int&

4.引用只能引用一个对象,一个对象可以被多次引用。

7.判断

int main() {int a = 20;const int& re_a = a;re_a = 30;//错误,不能直接修改const变量}

 4.inline内联函数

https://www.cnblogs.com/chengxuyuancc/archive/2013/04/04/2999844.html

4.1 内联函数的引出

c++从c中继承的一个重要特征就是效率。假如c++的效率明显低于c的效率,那么就会有很大的一批程序员不去使用c++了。

4.2  预处理宏的缺陷

宏函数是预处理器进行的

内联的编译器处理的

预处理器宏存在问题的关键是我们可能认为预处理器的行为和编译器的行为是一样的。当然也是由于宏函数调用和函数调用在外表看起来是一样的,因为也容易被混淆。但是其中也会有一些微妙的问题出现:

问题一:

#define ADD(x,y) x+y
inline int Add(int x,int y){return x + y;
}
void test(){int ret1 = ADD(10, 20) * 10; //希望的结果是300int ret2 = Add(10, 20) * 10; //希望结果也是300cout << "ret1:" << ret1 << endl; //210cout << "ret2:" << ret2 << endl; //300
}

问题二:

#define COMPARE(x,y) ((x) < (y) ? (x) : (y))
int Compare(int x,int y){return x < y ? x : y;
}
void test02(){int a = 1;int b = 3;//cout << "COMPARE(++a, b):" << COMPARE(++a, b) << endl; // 3cout << "Compare(int x,int y):" << Compare(++a, b) << endl; //2
}

4.3 内联函数基本概念:空间换时间

在c++中,预定义宏的概念是用内联函数来实现的,而内联函数本身也是一个真正的函数。内联函数具有普通函数的所有行为。唯一不同之处在于内联函数会在适当的地方像预定义宏一样展开,所以不需要函数调用的开销。因此应该不使用宏,使用内联函数。

注意必须函数体和声明结合在一起,否则编译器将它作为普通函数来对待。

inline void func(int a);
inline int func(int a) {return a;
}

内联函数的确占用空间,但是内联函数相对于普通函数的优势只是省去了函数调用时候的压栈,跳转,返回的开销。我们可以理解为内联函数是以空间换时间

4.4 类内部的内联函数

为了定义内联函数,通常必须在函数定义前面放一个inline关键字。但是在类内部定义内联函数时并不是必须的。任何在类内部定义的函数自动成为内联函数。

class Person{
public:Person(){ cout << "构造函数!" << endl; }void PrintPerson(){ cout << "输出Person!" << endl; }
}

4.5 内联函数和编译器

4.6 注意点

  • 不能存在任何形式的循环语句
  • 不能存在过多的条件判断语句
  • 函数体不能过于庞大
  • 不能对函数进行取址操作

内联仅仅只是给编译器一个建议,编译器不一定会接受这种建议,如果你没有将函数声明为内联函数,那么编译器也可能将此函数做内联编译。一个好的编译器将会内联小的、简单的函数。

4.7 内联函数 VS 宏函数

4.8 总结

5. 函数的默认参数和占位函数

5.1 默认参数

c++在声明函数原型的时可为一个或者多个参数指定默认(缺省)的参数值,当函数调用的时候如果没有指定这个值,编译器会自动用默认值代替。

void TestFunc01(int a = 10, int b = 20){cout << "a + b  = " << a + b << endl;
}
//注意点:
//1. 形参b设置默认参数值,那么后面位置的形参c也需要设置默认参数
void TestFunc02(int a,int b = 10,int c = 10){}
//2. 如果函数声明和函数定义分开,函数声明设置了默认参数,函数定义不能再设置默认参数
void TestFunc03(int a = 0,int b = 0);
void TestFunc03(int a, int b){}int main(){//1.如果没有传参数,那么使用默认参数TestFunc01();//2. 如果传一个参数,那么第二个参数使用默认参数TestFunc01(100);//3. 如果传入两个参数,那么两个参数都使用我们传入的参数TestFunc01(100, 200);return EXIT_SUCCESS;
}

注意点:

5.2  函数的占位参数

c++在声明函数时,可以设置占位参数。占位参数只有参数类型声明,而没有参数名声明。一般情况下,在函数体内部无法使用占位参数。【占位符也是参数,必须传参数】

void TestFunc01(int a,int b,int){//函数内部无法使用占位参数cout << "a + b = " << a + b << endl;
}
//占位参数也可以设置默认值
void TestFunc02(int a, int b, int = 20){//函数内部依旧无法使用占位参数cout << "a + b = " << a + b << endl;
}
int main(){//错误调用,占位参数也是参数,必须传参数//TestFunc01(10,20); //正确调用TestFunc01(10,20,30);//正确调用TestFunc02(10,20);//正确调用TestFunc02(10, 20, 30);return EXIT_SUCCESS;
}

6. 函数重载(overload)

6.1 函数重载概述

    能使名字方便使用,是任何程序设计语言的一个重要特征!

在传统c语言中,函数名必须是唯一的,程序中不允许出现同名的函数。在c++中是允许出现同名的函数,这种现象称为函数重载。

函数重载的目的就是为了方便的使用函数名。

6.2 函数重载基本语法

实现函数重载的条件:

  1. 同一个作用域
  2. 参数个数不同
  3. 参数类型不同
  4. 参数顺序不同
  5. 返回值并不是构成函数重载的条件
//1. 函数重载条件
namespace A{void MyFunc(){ cout << "无参数!" << endl; }void MyFunc(int a){ cout << "a: " << a << endl; }void MyFunc(string b){ cout << "b: " << b << endl; }void MyFunc(int a, string b){ cout << "a: " << a << " b:" << b << endl;}void MyFunc(string b, int a){cout << "a: " << a << " b:" << b << endl;}
}
//2.返回值不作为函数重载依据
namespace B{void MyFunc(string b, int a){}//int MyFunc(string b, int a){} //无法重载仅按返回值区分的函数
}

注意: 函数重载和默认参数一起使用,需要额外注意二义性问题的产生。

为什么函数返回值不作为重载条件呢?

调用准则

#include	<iostream>
using namespace	std;
void	print(double	a) {cout << a << endl;
}
void print(int	a) {cout << a << endl;
}
int	main()
{print(1);	//	print(int)print(1.1);	//	print(double)print('a');	//	print(int)print(1.11f);	//	print(double)return 0;
}

编译器调用重载函数的准则:

6.3 重载底层实现(name mangling)

6.4 函数重载与函数默认参数

6.5 函数重载和函数指针

函数指针基本语法

#define _CRT_SECURE_NO_WARNINGS
#include <iostream>using namespace std;int func(int a, int b)
{cout << "func(int, int)" << endl;return 0;
}int func(int a, int b, int c)
{cout << "func(int, int,int )" << endl;return 0;
}//1 . 定义一种函数类型
typedef int(MY_FUNC)(int, int);//2 顶一个指向之中函数类型的指针类型
typedef int(*MY_FUNC_P)(int, int);int main(void)
{//1.MY_FUNC *fp = NULL;fp = func;fp(10, 20);//2.MY_FUNC_P fp1 = NULL;fp1 = func;fp1(10, 20);//3. int(*fp3)(int, int) = NULL;fp3 = func;fp3(10, 20);func(10, 20);func(10, 20, 30);fp3 = func; //fp3 ---> func(int,int)//实际上在给函数指针赋值的时候,是会发生函数重载匹配的//在调用函数指针的时候,所调用的函数就已经固定了。int(*fp4)(int, int, int) = NULL;fp4 = func; //fp4 ---> func(int,int,int)fp3(10, 30);//func(int,int)fp3(10, 20);fp4(10, 30, 30);return 0;
}

6.6 总结

7.类和对象

7.1 类和对象的基本概念

C和C++中struct区别

  1. c语言struct只有变量
  2. c++语言struct 既有变量,也有函数

访问控制权限

一个类类的内部,是默认private

我们编写程序的目的是为了解决现实中的问题,而这些问题的构成都是由各种事物组成,我们在计算机中要解决这种问题,首先要做就是要将这个问题的参与者:事和物抽象到计算机程序中,也就是用程序语言表示现实的事物。

//封装两层含义
//1. 属性和行为合成一个整体
//2. 访问控制,现实事物本身有些属性和行为是不对外开放
class Person{
//人具有的行为(函数)
public:void Dese(){ cout << "我有钱,年轻,个子又高,就爱嘚瑟!" << endl;}
//人的属性(变量)
public:int mTall; //多高,可以让外人知道
protected:int mMoney; // 有多少钱,只能儿子孙子知道
private:int mAge; //年龄,不想让外人知道
};int main(){Person p;p.mTall = 220;//p.mMoney 保护成员外部无法访问//p.mAge 私有成员外部无法访问p.Dese();return EXIT_SUCCESS;
}

sruct和class的区别

class A{int mAge;
};
struct B{int mAge;
};void test(){A a;B b;//a.mAge; //无法访问私有成员b.mAge; //可正常外部访问
}
#define _CRT_SECURE_NO_WARNINGS
#include <iostream>using namespace std;struct Hero
{char name[64];int sex;
};void printHero(struct Hero& h)
{cout << "Hero" << endl;cout << "name = " << h.name << endl;cout << "sex = " << h.sex << endl;
}class AdvHero
{
public://访问控制权限char name[64];int sex;void printHero(){cout << "advHero" << endl;cout << "name = " << name << endl;cout << "sex = " << sex << endl;}
};class Animal
{//{}以内 叫类的内部, 以外叫类的外部
public:char kind[64];char color[64];//在public下面定义成员变量和函数 是能够在类的内部和外部都可以访问的。void printAnimal(){cout << "kind = " << kind << endl;cout << "color = " << color << endl;}void write(){cout << kind << "开始鞋子了" << endl;}void run(){cout << kind << "跑起来了" << endl;}//
private://在private下面定义的成员变量和方法只能够在类的内部访问};int main(void)
{Hero h;strcpy(h.name, "gailun");h.sex = 1;printHero(h);AdvHero advH;strcpy(advH.name, "ChunBro");advH.sex = 1;advH.printHero();cout << "-----------" << endl;Animal dog;strcpy(dog.kind, "dog");strcpy(dog.color, "yellow");Animal sheep;strcpy(sheep.kind, "sheep");strcpy(sheep.color, "white");dog.write();sheep.run();return 0;
}

将成员变量设置为private

class AccessLevels{
public://对只读属性进行只读访问int getReadOnly(){ return readOnly; }//对读写属性进行读写访问void setReadWrite(int val){ readWrite = val; }int getReadWrite(){ return readWrite; }//对只写属性进行只写访问void setWriteOnly(int val){ writeOnly = val; }
private:int readOnly; //对外只读访问int noAccess; //外部不可访问int readWrite; //读写访问int writeOnly; //只写访问
};

7.2 用class去封装带行为的类

class 封装的本质,在于将数据和行为,绑定在一起然后能过对象来完成操 作。

#include	<iostream>
using namespace	std;
class	Date
{
public:void	init(Date & d);void	print(Date& d);bool	isLeapYear(Date& d);
private:int	year;int	month;int	day;
};
void	Date::init(Date& d)
{cout << "year,month,day:" << endl;cin >> d.year >> d.month >> d.day;
}
void	Date::print(Date& d)
{cout << "year	month	day" << endl;cout << d.year << ":" << d.month << ":" << d.day << endl;
}
bool	Date::isLeapYear(Date& d)
{if ((d.year % 4 == 0 && d.year % 100 != 0) || d.year % 400 == 0)return true;elsereturn false;
}
int	main()
{Date	d;d.init(d);d.print(d);if (d.isLeapYear(d))cout << "leap	year" << endl;elsecout << "not	leap	year" << endl;return 0;
}

7.3 类的封装

一般类中的属性是private

#define _CRT_SECURE_NO_WARNINGS
#include <iostream>using namespace std;struct Date
{int year;int month;int day;
};void init_date(struct Date & d)
{cout << "year, month, day" << endl;cin >> d.year;cin >> d.month;cin >> d.day;
}//打印data的接口
void print_date(struct Date &d)
{cout << d.year << "年" << d.month << "月" << d.day << "日" << endl;
}bool is_leap_year(struct Date &d)
{if (((d.year % 4 == 0) && (d.year % 100 != 0)) || (d.year % 400 == 0)) {return true;}return false;
}class MyDate
{
public://成员方法 成员函数void init_date(){cout << "year, month, day" << endl;cin >> year;cin >> month;cin >> day;}//打印data的接口void print_date(){cout << year << "年" << month << "月" << day << "日" << endl;}bool is_leap_year(){if (((year % 4 == 0) && (year % 100 != 0)) || (year % 400 == 0)) {return true;}return false;}int get_year(){return year;}void set_year(int new_year){year = new_year;}protected://保护控制权限。在类的继承中跟private有区别,在单个类中,跟private是一抹一样。
private:int year;int month;int day;
};//一个类类的内部,默认的访问控制权限是private
class Hero
{int year;
};//一个结构体默认的访问控制权限的是public
struct Hero2
{int year;void print(){}
};int main(void)
{
#if 0Date d1;init_date(d1);print_date(d1);if (is_leap_year(d1) == true) {cout << "是闰年 " << endl;}else {cout << "不是闰年 " << endl;}
#endifMyDate my_date;my_date.init_date();my_date.print_date();if (my_date.is_leap_year() == true){cout << "是闰年 " << endl;}else {cout << "不是闰年 " << endl;}//getter,settercout << my_date.get_year() << endl;my_date.set_year(2000);cout << my_date.get_year() << endl;Hero h;//h.year = 1000;Hero2 h2;h2.year = 100;return 0;
}

7.4 ⾯向对象编程

#define _CRT_SECURE_NO_WARNINGS
#include <iostream>using namespace std;//面向对象
class Dog
{
public:void eat(char *food){cout << name << "吃" << food << endl;}char name[64];
};//面向过程
void eat(class Dog &dog, char *food)
{cout << dog.name << "吃" << food << endl;
}int main(void)
{Dog dog;strcpy(dog.name, "狗");eat(dog, "翔");dog.eat("翔");return 0;
}

 求圆的面积和周长

#define _CRT_SECURE_NO_WARNINGS
#include <iostream>using namespace std;//圆的周长
double getCircleGirth(double r)
{return 2 * 3.14 * r;
}//源的面积
double getCircleArea(double r)
{return 3.14 * r * r;
}//用面向对象实现//圆类
class Circle
{
public:void setR(double r){m_r = r;}double getR(){return m_r;}double getGirth(){return 2 * 3.14 * m_r;}double getArea(){return m_r * m_r * 3.14;}private:double m_r; //圆的私有成员 半径
};class Circle2
{
public:void setR(double r){m_r = r;}double getR(){return m_r;}double getArea(){m_area = m_r * m_r * 3.14;return m_area;}double getGirth(){m_girth = m_r * 2 * 3.14;return m_girth;}private:double m_r;double m_girth; //周长double m_area;//面积
};int main(void)
{double r = 10; //圆的半径double g = 0;double a = 0;g = getCircleGirth(r);a = getCircleArea(r);cout << "圆的半径是" << r << endl;cout << "圆的周长是" << g << endl;cout << "圆的面积是" << a << endl;cout << "------" << endl;Circle c;c.setR(10);cout << "圆的半径是" << c.getR() << endl;cout << "圆的周长是" << c.getGirth() << endl;cout << "圆的面积是" << c.getArea() << endl;cout << "------------" << endl;Circle2 c2;c2.setR(10);cout << "圆的半径是" << c2.getR() << endl;cout << "圆的周长是" << c2.getGirth() << endl;cout << "圆的面积是" << c2.getArea() << endl;return 0;
}

圆的周长和面积多文件编写

Circle.h

#pragma once#if 0
#ifndef __CIRCLE_H_
#define __CIRCLE_H_#endif
#endifclass Circle
{
public://设置半径:void setR(double r);//得到半径double getR();double getArea();double getGirth();private:double m_r;double m_area;double m_girth;
};

Circle.cpp

#include "Circle.h"//Circle::表示还在圆的内部
void Circle::setR(double r)
{m_r = r;
}double Circle::getR()
{return m_r;
}double Circle::getArea()
{m_area = m_r *m_r *3.14;return m_area;
}double Circle::getGirth()
{m_girth = m_r * 2 * 3.14;return m_girth;
}

mian.cpp

#define _CRT_SECURE_NO_WARNINGS
#include <iostream>#include "Circle.h"using namespace std;int main(void)
{Circle c;c.setR(10);cout << "面积" << c.getArea() << endl;return 0;
}

判断两个立方体是否相等

#define _CRT_SECURE_NO_WARNINGS
#include <iostream>using namespace std;//立方体类
class Cube
{
public:void setABC(int a, int b, int c){m_a = a;m_b = b;m_c = c;}int getArea(){return (m_a*m_b) * 2 + (m_a*m_c) * 2 + (m_b*m_c) * 2;}int getVolume(){return (m_a*m_b*m_c);}int getA(){return m_a;}int getB(){return m_b;}int getC(){return m_c;}//同类之间无私处bool judgeCube(Cube &another){if (m_a == another.m_a &&m_b == another.getB() &&m_c == another.getC()) {return true;}else {return false;}}
private:int m_a;int m_b;int m_c;
};//全局函数
bool judgeCube(Cube &c1, Cube &c2)
{if (c1.getA() == c2.getA() &&c1.getB() == c2.getB() &&c1.getC() == c2.getC()) {return true;}else {return false;}
}int main(void)
{Cube c1;c1.setABC(10, 20, 30);Cube c2;c2.setABC(10, 20, 30);cout << "c1 的体积是" << c1.getVolume() << endl;cout << "c1 的面积是" << c1.getArea() << endl;if (judgeCube(c1, c2) == true) {cout << "相等" << endl;}else {cout << "不相等" << endl;}cout << " ------ " << endl;if (c1.judgeCube(c2) == true) {cout << "相等" << endl;}else {cout << "不相等" << endl;}return 0;
}

判断点是否在圆的内部

#define _CRT_SECURE_NO_WARNINGS
#include <iostream>using namespace std;//点类
class Point
{
public:void setXY(int x, int y){m_x = x;m_y = y;}int getX(){return m_x;}int getY(){return m_y;}
private:int m_x;int m_y;
};//圆类
class Circle
{
public:void setXY(int x, int y){x0 = x;y0 = y;}void setR(int r){m_r = r;}//提供一个判断点是否在圆内//true 在内部//false 在外部bool judgePoint(Point &p){int dd;dd = (p.getX() - x0)*(p.getX() - x0) + (p.getY() - y0)*(p.getY() - y0);if (dd > m_r*m_r) {return false;}else {return true;}}private:int x0;int y0;int m_r;
};int main(void)
{Circle c;c.setXY(2, 2);c.setR(4);Point p;p.setXY(8, 8);if (c.judgePoint(p) == true) {cout << "圆的内部" << endl;}else {cout << "圆的外部" << endl;}return 0;
}

判断两个圆是否相交

#include<iostream>
using namespace std;
class Point {
public:void setXY(int x, int y) {m_x = x;m_y = y;}//计算两个点之间的距离double pointDistance(Point& another) {int dis_x = m_x - another.m_x;int dis_y = m_y - another.m_y;//斜边double dis = sqrt(dis_x * dis_x + dis_y * dis_y);return dis;}private:int m_x;int m_y;
};
class Circle {
public:void setR(int r) {m_r = r;}void setXY(int x1, int y1) {p0.setXY(x1, y1);}//判断圆是否相交bool isConnection(Circle& another) {//两个圆的半径之和int r = m_r + another.m_r;//两个圆心之间的距离double dis = p0.pointDistance(another.p0);if (dis <= r) {			//相交return true;}else {return false;}}private:int m_r;Point p0;
};int main(void)
{Circle c1, c2;int x, y, r;cout << "请输入第一个圆的半径" << endl;cin >> r;c1.setR(r);cout << "请输入第一个圆的x" << endl;cin >> x;cout << "请输入第一个圆的y" << endl;cin >> y;c1.setXY(x, y);cout << "请输入第2个圆的半径" << endl;cin >> r;c2.setR(r);cout << "请输入第2个圆的x" << endl;cin >> x;cout << "请输入第2个圆的y" << endl;cin >> y;c2.setXY(x, y);if (c1.isConnection(c2) == true) {cout << "相交" << endl;}else {cout << "不想交" << endl;}return 0;
}

相关文章:

C++【个人笔记1】

1.C的初识 1.1 简单入门 #include<iostream> using namespace std; int main() {cout << "hello world" << endl;return 0; } #include<iostream>; 预编译指令&#xff0c;引入头文件iostream.using namespace std; 使用标准命名空间cout …...

博通强迫三星签不平等长约,被韩处罚1亿元 | 百能云芯

近日&#xff0c;博通&#xff08;Broadcom&#xff09;这家国际知名的半导体公司因其市场主导地位的滥用&#xff0c;遭到了韩国公平贸易委员会&#xff08;FTC&#xff09;的严厉制裁&#xff0c;罚款高达191亿韩元&#xff0c;约合人民币1.04亿元。这一惩罚背后的故事揭示了…...

版本控制 Sourcetree

Sourcetree软件做版本控制&#xff0c;小程序的代码和springboot项目的代码放到同一个文件夹下&#xff0c; 无脑安装就行 命名就用项目名bkd表示springboot项目名 项目命名xcx表示小程序 每次上传代码&#xff0c;一定要先拉下代码不然代码冲突处理起来比较麻烦...

题目 1059: 二级C语言-等差数列

题目描述 sum2581114…&#xff0c;输入正整数n&#xff0c;求sum的前n项和。样例输入 2样例输出 7 根据题目我们得知&#xff0c;求一个等差数列的和。 等差数列的下一项前一项d。d是等差。 根据这个直接求每一项&#xff0c;再加进sum的和&#xff0c;最后输出即可。 在本题中…...

HarmonyOS 如何使用异步并发能力进行开发

一、并发概述 并发是指在同一时间段内&#xff0c;能够处理多个任务的能力。为了提升应用的响应速度与帧率&#xff0c;以及防止耗时任务对主线程的干扰&#xff0c;HarmonyOS 系统提供了异步并发和多线程并发两种处理策略。 ● 异步并发是指异步代码在执行到一定程度后会被暂…...

时间格式化时候HH和hh的区别

SimpleDateFormat simpleDateFormatnew SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); simpleDateFormat.format(new Date()) HH&#xff08;大写&#xff09;&#xff1a;表示使用24小时制&#xff08;也称为军用时间制&#xff09;来表示小时。它的范围是从00到23。例…...

aliyunoss上传图片

依赖 <dependency><groupId>com.aliyun.oss</groupId><artifactId>aliyun-sdk-oss</artifactId><version>3.8.1</version></dependency>配置文件 config:alioss:endpoint: oss-cn-shanghai.aliyuncs.com&#xff08;节点名 我…...

动手吧,vue数字动画

数字动画&#xff0c;有数字的地方都能用上&#xff0c;拿去吧&#xff01; 效果&#xff1a; 1、template部分 <template><div class"v-count-up">{{ dispVlaue }}</div> </template> 2、js部分 export default {data() {return {timer…...

Android12之仿Codec2.0实现传递编解码器组件本质(四十六)

简介: CSDN博客专家,专注Android/Linux系统,分享多mic语音方案、音视频、编解码等技术,与大家一起成长! 优质专栏:Audio工程师进阶系列【原创干货持续更新中……】🚀 人生格言: 人生从来没有捷径,只有行动才是治疗恐惧和懒惰的唯一良药. 更多原创,欢迎关注:Android…...

MongoDB【部署 04】Windows系统实现MongoDB多磁盘存储

Windows系统实现多磁盘存储 1.为什么2.多磁盘存储2.1 数据库配置2.2 文件夹磁盘映射2.3 创建新的数据集 3.总结 1.为什么 这里仅针对只有一台Windows系统服务器的情景&#xff1a; 当服务器存储不足时&#xff0c;或者要接入更多的数据&#xff0c;就会挂载新磁盘&#xff0c…...

ruoyi框架使用自定义用户表登录

背景 有的时候我们做框架升级或改造的时候&#xff0c;需要用到原来的部分表&#xff0c;比如只是用ruoyi的框架&#xff0c;然后登录的用户逻辑还是想用自己的表&#xff0c;那么接下来这边文章将介绍修改逻辑。 修改教程 1、SysLoginController.java 大家找到这个login方…...

计算机视觉与深度学习-卷积神经网络-卷积图像去噪边缘提取-卷积-[北邮鲁鹏]

目录标题 参考学习链接卷积的定义卷积的性质叠加性平移不变性交换律结合律分配律标量 边界填充边界填充方法 - 常数填充最常用常数填充零填充&#xff08;zero padding&#xff09;拉伸镜像 卷积示例单位脉冲核无变化平移平滑锐化 卷积核平均卷积核高斯卷积核高斯卷积核定义高斯…...

JS手动实现发布者-订阅者模式

发布-订阅模式是一种对象间一对多的依赖关系&#xff0c;当一个对象的状态发送改变时&#xff0c;所有依赖于它的对象都将得到状态改变的通知。具体过程是&#xff1a;订阅者把自己想订阅的事件注册到调度中心&#xff0c;当发布者更新该事件时通知调度中心&#xff0c;由调度中…...

【含面试题】MySQL死锁日志分析与解决的Java代码实现

AI绘画关于SD,MJ,GPT,SDXL百科全书 面试题分享点我直达 2023Python面试题 2023最新面试合集链接 2023大厂面试题PDF 面试题PDF版本 java、python面试题 项目实战:AI文本 OCR识别最佳实践 AI Gamma一键生成PPT工具直达链接 玩转cloud Studio 在线编码神器 玩转 GPU AI…...

解决方案:TSINGSEE青犀+智能分析网关助力智慧仓储智能化监管

为全面保障物流仓储的安全性与完整性&#xff0c;解决仓库管理难题&#xff0c;优化物流仓储方式&#xff0c;提升仓储效率&#xff0c;降低人工成本&#xff0c;旭帆科技推出智慧仓储AI视频智能分析方案&#xff0c;利用物联网、大数据、云计算等技术&#xff0c;对仓储管理进…...

进程间通信

#include <unistd.h> int pipe(int pipefd[2]); 功能&#xff1a;创建一个匿名管道&#xff0c;用于进程间通信 参数&#xff1a; -int pipefd[2]:传出参数 pipefd[0]对应的是管道的读端 pipefd[0]对应的是管道的写端 返回值&#xff1a; 成功返回0&#xff0c;失败返回-…...

Ubuntu 22.04.3 LTS安装

最近换电脑了&#xff0c;准备重新装一下ubuntu。多年前装过ubuntu很老的版本&#xff0c;现在发现官网最新的LTS版本是 Ubuntu 22.04.3 LTS 版本。那重新装的话&#xff0c;肯定装最新的版本了。这里我记录下自己的安装过程&#xff0c;作为以后的笔记查看。 我的环境&#x…...

记一次manjaro-i3系统sogoupinying候选词无法正常显示中文(变方框了)问题解决方案

记一次manjaro-i3系统sogoupinying候选词无法正常显示中文&#xff08;变方框了&#xff09;问题解决方案 前言解决方案 前言 今天早上发现公司电脑显卡驱动好像坏了&#xff0c;各种折腾完了干脆把系统搞黑屏无法开机了&#xff0c;时间有限懒再修了&#xff0c;于是重装了系…...

Lua学习笔记:词法分析

前言 本篇在讲什么 Lua的词法分析 本篇需要什么 对Lua语法有简单认知 对C语法有简单认知 依赖Visual Studio工具 本篇的特色 具有全流程的图文教学 重实践&#xff0c;轻理论&#xff0c;快速上手 提供全流程的源码内容 ★提高阅读体验★ &#x1f449; ♠ 一级标题…...

flask服务鉴权

基本认证&#xff08;Basic Authentication&#xff09;&#xff1a; 这是一种简单的鉴权方式&#xff0c;需要客户端发送用户名和密码&#xff0c;服务器验证后允许或拒绝访问。可以使用 Flask-BasicAuth 扩展来实现。首先&#xff0c;安装扩展&#xff1a; pip install Fla…...

【2023华为杯B题】DFT类矩阵的整数分解逼近(思路及代码下载)

&#x1f4a5;&#x1f4a5;&#x1f49e;&#x1f49e;欢迎来到本博客❤️❤️&#x1f4a5;&#x1f4a5; &#x1f3c6;博主优势&#xff1a;&#x1f31e;&#x1f31e;&#x1f31e;博客内容尽量做到思维缜密&#xff0c;逻辑清晰&#xff0c;为了方便读者。 ⛳️座右铭&a…...

基于微信小程序的校园生活管理系统设计与实现(源码+lw+部署文档+讲解等)

文章目录 前言运行环境学生微信端的主要功能有&#xff1a;管理员的主要功能有&#xff1a;具体实现截图视频演示为什么选择我自己的网站自己的小程序&#xff08;小蔡coding&#xff09;有保障的售后福利 代码参考源码获取 前言 &#x1f497;博主介绍&#xff1a;✌全网粉丝1…...

SQL server 创建存储过程

SQL Server如何创建存储过程 存储过程&#xff1a; 可以理解为完成特定功能的一组 SQL 语句集&#xff0c;存储在数据库中&#xff0c;经过第一次编译&#xff0c;之后的运行不需要再次编译&#xff0c;用户通过指定存储过程的名字并给出参数&#xff08;如果该存储过程带有参数…...

一文了解亚马逊云科技适用于 Amazon Lightsail 的托管数据库

Amazon Lightsail 是亚马逊云科技提供的一种易上手使用、月度价格经济实惠&#xff0c;并包括了计算实例、容器、存储、数据库的虚拟专用服务器。在创建时可以进行业务蓝图选择&#xff0c;可选择包含多种操作系统&#xff08;Linux/Windows 等&#xff09;或操作系统加上典型应…...

【antd Col】奇怪的TypeError: Cannot read properties of undefined (reading ‘then‘)

现象 修改antd的Col组件的layouts属性为span后&#xff0c;并通过监听resize事件对span列宽进行动态变化时&#xff0c;报错TypeError: Cannot read properties of undefined (reading ‘then‘)。 补充示例一 由于我使用了飞冰ice.js&#xff0c;且在以下过程中写了如下语句…...

requests处理 multipart/form-data 请求以及 boundary值问题

requests处理 multipart/form-data 请求以及 boundary值问题 前言1. 请求需要携带本地资源2. 请求需要携带json3. 总结 前言 关于 Content-type: multipart/form-data可以看一下这篇文章, 分析特别详细 HTTP协议之multipart/form-data请求分析 put和post区别不大, 只是上传资…...

FBX文件结构解读【文本格式】

FBX 格式几乎受到所有 3D 引擎的支持&#xff0c;是 Autodesk 开发的 3D 模型的专有格式。它支持顶点、索引、法线、UV坐标、材质和动画。 FBX还支持许多其他类型的信息&#xff0c;但它们对游戏引擎几乎没有用处。 推荐&#xff1a;用 NSDT编辑器 快速搭建可编程3D场景 有两种…...

JS基础语法

JS是一门面向对象的编程语言&#xff0c;运行在客户端的脚本语言&#xff0c;可以基于Node.js进行服务器端编程 JS的作用: 表单动态校验网页特效服务端开发 浏览器执行JS&#xff1a; 浏览器分为两部分&#xff1a;渲染引擎和JS引擎 渲染引擎用来解析HTML和CSS&#xff0c;…...

【Zabbix监控一】zabbix的原理与安装

利用一个优秀的监控软件&#xff0c;我们可以: ●通过一个友好的界面进行浏览整个网站所有的服务器状态 ●可以在 Web 前端方便的查看监控数据 ●可以回溯寻找事故发生时系统的问题和报警情况 总结&#xff1a;zabbix主要功能 监控&#xff0c;cpu负载&#xff0c;内存使用&a…...

图的十字链表存储结构

1.其实就是邻接表和逆邻接表的结合&#xff0c;说明白点&#xff0c;就是用箭头表示出弧头&#xff0c;弧尾&#xff0c;以及他们之间的关系 2.顶点结构 3.弧结构 3.这样根据上面的结点十字链表结构就很好分析了...

seo 网站优化/网页广告怎么投放

我们都知道github是一个巨大的开源宝库&#xff0c;上面有非常多的优质项目&#xff0c;我们经常需要去上面下载优秀的项目来进行学习或者科研等等。但是啊&#xff0c;我们经常遇到一个痛点&#xff0c;就是在clone的时候&#xff0c;下载速度太慢了&#xff0c;经常就就几kb不…...

骏域建网站/官方网站百度一下

2019独角兽企业重金招聘Python工程师标准>>> 说道La(n)mp开发&#xff0c;其实我个人觉得应该把这个单词倒过来&#xff0c;可能才更能表现出这套技术栈的主次和先后顺序&#xff1a;pmalphpmysqlapache\nginxlinux。 PHP 手册要仔细读 &#xff08;高&#xff09; …...

荆门网站建设514885/百度销售系统

Android10.0默认的主界面程序是谷歌开发的Launcher3&#xff0c;现在有关闭主界面程序的需求。我们的思路比较简单&#xff1a;去掉Launcher3编译生成的apk。 禁掉Launcher3源码的编译&#xff1a; mv packages/apps/Launcher3/Android.mk packages/apps/Launcher3/Android.mk…...

模板网站代码/百度24小时人工客服电话

来源&#xff1a;https://www.ibm.com/support/knowledgecenter/zh/SSHEB3_3.3.2/com.ibm.tap.doc_3.3.2/loc_topics/c_custom_date_formats.html 定制日期格式 您可以通过 IBM TRIRIGA Application Platform 随附的产品定义不同的日期格式或日期时间格式。 在“列表管理器”中…...

网站建设与推广的销售/苏州网络推广服务

package day06;import java.util.Scanner;public class Date08 {public static void main(String[] args) {/*** 键盘录入一个字符串&#xff0c;用代码判断大小写和数字出现的次数* 大写字母字符范围 65-90* 小写字母字符范围97-122* 数字0-9数字范围48-57* 分析&#xff1a;1…...

东南亚购物网站排名/百度代理公司

1.core dump介绍 程序异常退出&#xff08;crash&#xff09;时会自动生成一个core文件&#xff0c;包含了程序运行时的内存&#xff0c;寄存器状态&#xff0c;堆栈指针&#xff0c;内存管理等信息&#xff0c;也就是把程序当时工作的状态存储成一个文件。不仅仅是在出错的时候…...