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

C/C++预处理过程

目录

前言:

1. 预定义符号

2. #define定义常量

3. #define定义宏

4. 带有副作用的宏参数

5.  宏替换的规则

6. 宏和函数的对比

7. #和##

8.  命名约定

9.  #undef

10.  命令行定义

11.  条件编译

12.  头文件的包含

13.  其他预处理指令

总结:。


前言:

本篇介绍c/c++的预处理过程,c和c++在预处理阶段基本相同。

1. 预定义符号

c语言定义了一些预处理的符号,这些是可以直接使用的,并且这些符号也是在预处理期间完成的。

  • __FILE__ //进⾏编译的源⽂件
  • __LINE__ //⽂件当前的⾏号
  • __DATE__ //⽂件被编译的⽇期
  • __TIME__ //⽂件被编译的时间
  • __STDC__ //如果编译器遵循ANSI C,其值为1,否则未定义

2. #define定义常量

例如我们定义100为一个MAX,后面使用MAX都会在预处理阶段替换为100。

#define MAX 100

如果我们觉得定义的东西太长了,也可以分行写,在结尾加上反斜杠\即可:

#define DEBUG_PRINT printf("file:%s\tline:%d\t \date:%s\ttime:%s\n" ,\__FILE__,__LINE__ , \__DATE__,__TIME__ )

现在来考虑一个问题:

在定义常量的时候,要不要加上引号???

#define MAX 1000;
#define MAX 1000

 其实通过#define的性质就可以知道,它在预处理阶段做的只是替换工作,如果将代码放到下面的情况下就会出错:

if(condition)max = MAX;
elsemax = 0;

 这样if后面就是两条语句了,而由于if如果不加大括号匹配的只有一条语句,所以这样else就没法匹配了,就出错了。

 

3. #define定义宏

#define机制包括了一个规定,允许把参数替换到文本中,这种实现通常称为宏(macro)或定义宏(define macro)。

语法为:

#define name( parameter-list ) stuff

注意参数列表的括号必须要与name之间没有空格,不然参数列表就被识别为右边的内容了。

 

例如我们现在实现一个宏来实现乘法:

#define SQUARE( x ) x * x

可这样能表达我们想要的意思吗???

我们要注意宏仅仅是替换,所以在打印下面的情况下,就会出错:

	int a = 5;printf("%d\n", SQUARE(a + 1));//结果是11

我们想表达的是(5+1)*(5+1),而结果却是11,这就是因为宏仅仅是替换,只是替换为了a+1*a+1,所以我们加上扩号就能达到预期的效果了。

#define SQUARE(x) (x)*(x)

可这就完了吗?来看下面的代码,我们使用宏了实现一个相加:

#define DOUBLE(x) (x) + (x)

看着我们好像加上了括号好像就不会出现问题了,但是如果是下面的场景:

int a = 5;
printf("%d\n" ,10 * DOUBLE(a));//结果是55,而我们预期的是100

这是因为预处理阶段,宏被替换成了10*(5)+(5),所以我们还需要再加上一个括号:
 

1 #define DOUBLE( x) ( ( x ) + ( x ) )

所以我们得出结论:

所以用于对数值表达式进行求值的宏定义都应该用这种方式加上括号,避免在使用宏时由于参数中的操作符或邻近操作符之间不可预料的相互作用。

4. 带有副作用的宏参数

#define MAX(a, b) ( (a) > (b) ? (a) : (b) )
	int x = 5;int y = 8;int z = MAX(x++, y++);printf("x=%d y=%d z=%d\n", x, y, z);

这样带有自增自减的是具有副作用的,再给宏传参就出错了。

结果是 x=6,y=10,z=9(尽管最后执行的是z=(y++),后置++--改变的是自己,返回的是一个没有改变的值,所以这里z是9),这样的结果不仅对xyz进行了永久性的改变,而且比较是也不是预期的结果。

所以当宏参数在宏的定义时出现超过了一次(就像上面的案例),如果参数带有副作用,也就是自增自减类的,此时使用宏就可能出错。

 

5.  宏替换的规则

在程序中扩展#define定义符号和宏时,需要涉及几个步骤。
1. 在调用宏时,首先对参数进行检查,看看是否包含任何由#define定义的符号。如果是,它们首先被替换。
2. 替换文本随后被插入到程序中原来文本的位置。对于宏,参数名被他们的值所替换。
3. 最后,再次对结果文件进行扫描,看看它是否包含任何由#define定义的符号。如果是,就重复上述处理过程。

注意:
1. 宏参数和#define 定义中可以出现其他#define定义的符号。但是对于宏,不能出现递归。
#define string1 string
#define string "1abcd"printf("%s\n", string);printf("%s\n", string1);

2. 当预处理器搜索#define定义的符号的时候,字符串常量的内容并不被搜索,也就是说定义的符号不能是字符串常量。

6. 宏和函数的对比

宏通常用来执行简单的计算。比如在两个数中找出一个较大的时,写成下面的宏,更有优势:

#define MAX(a, b) ((a)>(b)?(a):(b))

为什么不用函数来实现呢?

1.

用于调用函数和从函数返回的代码可能比实际执行这个小型计算工作所需要的时间更多。所以宏比函数在程序的规模和速度方面更胜⼀筹。
2.
更为重要的是函数的参数必须声明为特定的类型。所以函数只能在类型合适的表达式上使用。反之这个宏可以适用于整形、长整型、浮点型等可以用于 > 来比较的类型。宏的参数是类型无关。

 但是相比函数,宏也有它的劣势:

1. 每次使用宏的时候,一份宏定义的代码将插入到程序中。除非宏比较短,否则可能大幅度增加程序的长度。
2. 宏是没法调试的。
3. 宏由于类型无关,也就不够严谨。
4. 宏可能会带来运算符优先级的问题,导致程容易出现错。

但其实宏也可以做到函数做不到的事情,例如宏的参数可以出现类型,但是函数做不到:

#define MALLOC(num, type)\(type*)malloc(num*sizeof(type))//使⽤MALLOC(10, int);//类型作为参数
//预处理器替换之后:(int*)malloc(10*sizeof(int));

宏和函数的对比:

 

7. #和##

#运算符是将宏的一个参数转换为字符串字面量,它运行出现在带参数的宏的替换列表中。

#define PRINT(n) printf("the value of "#n " is %d", n);

 如果定义有一个a为10,现在使用宏传a过去,就打印出来the value of a is 10 ,注意这里#n要加上一个引号,不然就被识别为printf打印的内容了,就直接打印出来一个#n,而不是预处理得到的了。 就理解为如果#n要在printf里识别为字符串,就要加上""。而直接这样使用就不用:

#define PRINT(n) #nint a=10;
printf("%s\n",PRINT(a));//结果是a

##运算符

//宏定义
#define GENERIC_MAX(type) \
type type##_max(type x, type y)\
{ \return (x>y?x:y); \
}GENERIC_MAX(int) //替换到宏体内后int##_max ⽣成了新的符号 int_max做函数名
GENERIC_MAX(float) //替换到宏体内后float##_max ⽣成了新的符号 float_max做函数名int main()
{//调⽤函数int m = int_max(2, 3);printf("%d\n", m);float fm = float_max(3.5f, 4.5f);printf("%f\n", fm);return 0;
}

 实际用的很少,不再过多解释。

8.  命名约定

一般来说函数和宏的使用语法是很相似的,所以语言本身没法帮我们区分二者。

所以命名习惯就是:

宏名全部大写,函数名不要全部大写。

9.  #undef

用于移除一个宏定义。

#undef NAME
//如果现存的⼀个名字需要被重新定义,那么它的旧名字⾸先要被移除。

10.  命令行定义

许多C 的编译器提供了⼀种能力,
允许在命令行中定义符号。用于启动编译过程。
例如:当我们根据同⼀个源文件要编译出⼀个程序的不同版本的时候,这个特性有点用处。(假定某个程序中声明了⼀个某个长度的数组,如果机器内存有限,我们需要⼀个很小的数组,但是另外一个机器内存大些,我们需要一个数组能够大些。)
#include <stdio.h>
int main()
{int array [ARRAY_SIZE];int i = 0;for(i = 0; i< ARRAY_SIZE; i ++){array[i] = i;}for(i = 0; i< ARRAY_SIZE; i ++){printf("%d " ,array[i]);}printf("\n" );return 0;
}
//linux 环境演⽰
gcc -D ARRAY_SIZE=10 programe.c

11.  条件编译

在编译⼀个程序的时候我们如果要将⼀条语句(⼀组语句)编译或者放弃是很⽅便的。因为我们有条件编译指令。
调试性的代码,删除可惜,保留⼜碍事,所以我们可以选择性的编译:
#include <stdio.h>
#define __DEBUG__
int main()
{int i = 0;int arr[10] = { 0 };for (i = 0; i < 10; i++){arr[i] = i;
#ifdef __DEBUG__printf("%d\n", arr[i]);//为了观察数组是否赋值成功。 
#endif //__DEBUG__}return 0;
}

如果我们不定义__DEBUG__这个宏,就什么也不会输出。

常见的条件编译指令:

1.
#if 常量表达式//...
#endif
//常量表达式由预处理器求值。
如:
#define __DEBUG__ 1
#if __DEBUG__//..
#endif
2.多个分⽀的条件编译
#if 常量表达式//...
#elif 常量表达式//...
#else//...
#endif
3.判断是否被定义
#if defined(symbol)
#ifdef symbol
#if !defined(symbol)
#ifndef symbol
4.嵌套指令
#if defined(OS_UNIX)#ifdef OPTION1unix_version_option1();
#endif#ifdef OPTION2unix_version_option2();#endif
#elif defined(OS_MSDOS)#ifdef OPTION2msdos_version_option2();#endif
#endif

12.  头文件的包含

首先,查找策略:

先在源⽂件所在⽬录下查找,如果该头⽂件未找到,编译器就像查找库函数头⽂件⼀样在
标准位置(标准路径)查找头⽂件。如果找不到就提⽰编译错误。

linux下标准头文件的路径:

/usr/include

windows下(按照自己的安装路径去找):

C:\Program Files (x86)\Microsoft Visual Studio 12.0\VC\include

然后就是库文件的包含:

1 #include <filename.h>
查找头文件直接去标准路径下去查找,如果找不到就提示编译错误。

当然库文件也可以使用""的形式包含,答案是可以的,但是这样不容易区分是库文件还是本地文件,查找的效率会低(尖括号是到系统路径下查找头文件,双引号是先在当前目录下查找头文件,如果没有找到,就再到系统的路径下去找)。 

嵌套文件的包含:

#include的替换方式就是预处理器先删除这条指令,并用包含文件的内容替换,但如果一个头文件被包含了10次,那实际就被编译了10次,如果重复包含,对编译的压力就会比较大,因为.h的文件会将内容拷贝10分到.c文件中去,这样预处理后代码量就会激增。如果有工程比较大,用公共使用的头文件,被大家都能使用,又不做处理,工程量会非常大。

如何解决?使用条件编译:

可以在每个头文件中的开头写:

#ifndef __TEST_H__
#define __TEST_H__//头⽂件的内容#endif //__TEST_H__,写在头文件结尾

也就是如果.h文件第一次被包含,此时__TEST_H__还没有被定义,所以执行#ifdef与#endif之间的代码,再次包含时,条件为假,因为以及有__TEST_H__的定义了,所以直接走到#endif,也就是什么也不执行。 

或者

 

#pragma once

13.  其他预处理指令

#error
#pragma
#line
......

具体可以用到的时候再查。

注:
推荐《⾼质量C/C++编程指南》中附录的考试试卷(很重要)。
笔试题:
1. 头⽂件中的 ifndef/define/endif是⼲什么⽤的?
2. #include <filename.h> 和 #include "filename.h" 有什么区别?

总结:

对于一些预处理阶段的一些不常用的可以选择性学习,但要知道,重点关注面试题相关的。

相关文章:

C/C++预处理过程

目录 前言&#xff1a; 1. 预定义符号 2. #define定义常量 3. #define定义宏 4. 带有副作用的宏参数 5. 宏替换的规则 6. 宏和函数的对比 7. #和## 8. 命名约定 9. #undef 10. 命令行定义 11. 条件编译 12. 头文件的包含 13. 其他预处理指令 总结&#x…...

客服电话系统:专业、便捷的服务沟通桥梁

一、引言 1.客服电话系统在现代服务中的重要性 在信息化时代&#xff0c;服务行业的竞争日益激烈&#xff0c;提供高效、便捷的服务成为企业赢得市场、获取用户信任的关键。客服电话系统作为企业与用户之间的重要沟通桥梁&#xff0c;不仅承载着解答疑问、处理问题的职责&…...

IP地址与子网掩码

1 IP地址 1.1 IPv4与IPv6 1.2 IPv4地址详解 IPv4地址分4段&#xff0c;每段8位&#xff0c;共32位二进制数组成。 1.2.1 地址分类 这32位又被分为网络号和主机号两部分&#xff0c;根据网络号占用位数的不同&#xff0c;又可分为以下几类&#xff1a; A类地址&#xff1a;…...

Python爬取公众号封面图(零基础也能看懂)

&#x1f4da;博客主页&#xff1a;knighthood2001 ✨公众号&#xff1a;认知up吧 &#xff08;目前正在带领大家一起提升认知&#xff0c;感兴趣可以来围观一下&#xff09; &#x1f383;知识星球&#xff1a;【认知up吧|成长|副业】介绍 ❤️感谢大家点赞&#x1f44d;&…...

2024.4.6学习笔记

今日学习韩顺平java0200_韩顺平Java_对象机制练习_哔哩哔哩_bilibili 今日学习p315-p328 动态绑定机制 当调用方法对象的时候&#xff0c;该方法会和该对象的内存地址/运行类型绑定 当调用对象属性时&#xff0c;没有动态绑定机制&#xff0c;哪里声明&#xff0c;哪里使用 …...

2024年华为OD机试真题-查找一个有向网络的头节点和尾节点-Java-OD统一考试(C卷)

题目描述: 给定一个有向图,图中可能包含有环,图使用二维矩阵表示,每一行的第一列表示起始节点,第二列表示终止节点,如[0, 1]表示从0到1的路径。每个节点用正整数表示。求这个数据的首节点与尾节点,题目给的用例会是一个首节点,但可能存在多个尾节点。同时,图中可能含有…...

【Django开发】0到1美多商城项目md教程第5篇:短信验证码,1. 避免频繁发送短信验证码逻辑分析【附代码文档】

美多商城完整教程&#xff08;附代码资料&#xff09;主要内容讲述&#xff1a;欢迎来到美多商城&#xff01;&#xff0c;项目准备。展示用户注册页面&#xff0c;创建用户模块子应用。用户注册业务实现&#xff0c;用户注册前端逻辑。图形验证码&#xff0c;图形验证码接口设…...

云原生:应用敏捷,华为视角下的应用现代化

Gartner 也提出&#xff0c;到 2023 年&#xff0c;新应用新服务的数量将达到 5 亿&#xff0c;也即是说&#xff1a;“每个企业都正在成为软件企业”。据IDC 预测&#xff0c;到 2025 年三分之二的企业将成为多产的“软件企业”&#xff0c;每天都会发布软件版本。越来越多的企…...

【测试篇】接口测试

接口测试&#xff0c;可以用可视化工具 postman。 如何做接口测试&#xff1f;&#xff1f; 我们可以先在浏览器中随机进入一个网页&#xff0c;打开开发者工具&#xff08;F12&#xff09;。 随便找一个接口Copy–>Copy as cURL(bash) 打开postman 复制地址 进行发送。 …...

突破校园网限速:使用 iKuai 多拨分流负载均衡 + Clash 代理(内网带宽限制通用)

文章目录 1. 简介2. iKuai 部署2.1 安装 VMware2.2 安装 iKuai(1) 下载固件(2) 安装 iKuai 虚拟机(3) 配置 iKuai 虚拟机(4) 配置 iKuai(5) 配置多拨分流 2.3 测试速度 3. Clash 部署(1) 配置磁盘分区(2) 安装 Docker(3) 安装 Clash(4) 设置代理 4. 热点&#xff1a;一起瓜分互…...

03-JAVA设计模式-工厂模式详解

工厂模式 工厂设计模式是一种创建型设计模式&#xff0c;它提供了一种封装对象创建过程的机制&#xff0c;将对象的创建与使用分离。 这种设计模式允许我们在不修改客户端代码的情况下引入新的对象类型。 在Java中&#xff0c;工厂设计模式主要有三种形式&#xff1a;简单工厂…...

百度文心大模型推理成本降至1% / 马斯克起诉OpenAI |魔法半周报

我有魔法✨为你劈开信息大海❗ 高效获取AIGC的热门事件&#x1f525;&#xff0c;更新AIGC的最新动态&#xff0c;生成相应的魔法简报&#xff0c;节省阅读时间&#x1f47b; &#x1f525;资讯预览 百度文心大模型推理成本降至1%&#xff0c;与三星、荣耀等企业达成合作 马斯…...

Struts2的入门:新建项目——》导入jar包——》jsp,action,struts.xml,web.xml——》在项目运行

文章目录 配置环境tomcat 新建项目导入jar包新建jsp界面新建action类新建struts.xml,用来配置action文件配置Struts2的核心过滤器&#xff1a;web.xml 启动测试给一个返回界面在struts.xml中配置以实现页面的跳转&#xff1a;result再写个success.jsp最后在项目运行 配置环境 …...

git 标签功能操作以及回退

Git 标签功能允许开发者为特定的提交打上标签&#xff0c;以便后续能够方便地引用这些提交。标签通常用于标记重要的版本或里程碑&#xff0c;例如软件发布的版本号。与分支不同&#xff0c;标签指向的是固定的提交&#xff0c;一旦设置&#xff0c;就不能轻易更改。下面是一些…...

利用python实现文字转语音

代码如下&#xff1a; import pathlib import tkinter as tk import tkinter.ttk as ttk import tkinter.filedialog as filedialog import tkinter.messagebox as msgbox import pyttsx3class Application(tk.Tk):def __init__(self):super().__init__()self.title("文本…...

拾光坞N3 ARM 虚拟主机 i茅台项目

拾光坞N3 在Dcoker部署i茅台案例 OS&#xff1a;Ubuntu 22.04.1 LTS aarch64 cpu&#xff1a;RK3566 ram&#xff1a;2G 部署流程——》mysql——》java8——》redis——》nginx mysql # 依赖 apt update apt install -y net-tools apt install -y libaio* # 下载mysql wg…...

docker安装nacos,单例模式(standalone),使用mysql数据库

文章目录 前言安装创建文件夹"假装"安装一下nacos拷贝文件夹删除“假装”安装的nacos容器生成nacos所需的mysql表获取mysql-schema.sql文件创建一个mysql的schema 重新生成新的nacos容器 制作docker-compose.yaml文件查看网站 前言 此处有本人写得简易版本安装&…...

【运输层】传输控制协议 TCP

目录 1、传输控制协议 TCP 概述 &#xff08;1&#xff09;TCP 的特点 &#xff08;2&#xff09;TCP 连接中的套接字概念 2、可靠传输的工作原理 &#xff08;1&#xff09;停止等待协议 &#xff08;2&#xff09;连续ARQ协议 3、TCP 报文段的首部格式 1、传输控制协议…...

深入浅出 -- 系统架构之Keepalived搭建双机热备

Keepalived重启脚本双机热备搭建 ①首先创建一个对应的目录并下载keepalived安装包&#xff08;提取码:s6aq&#xff09;到Linux中并解压&#xff1a; [rootlocalhost]# mkdir /soft/keepalived && cd /soft/keepalived [rootlocalhost]# wget https://www.keepalived.…...

如何做好产业园运营?树莓集团:响应政府号召,规划,注重大局观

随着经济的发展和产业结构的调整&#xff0c;产业园区的建设和发展已经成为推动地方经济的重要力量。如何做好产业园运营&#xff0c;提高行业竞争力&#xff0c;现已成为了一个亟待解决的问题。树莓集团作为一家有着丰富产业园运营经验的企业&#xff0c;积极响应政府号召&…...

NIO与BIO

当谈到 Java 网络编程时&#xff0c;经常会听到两个重要的概念&#xff1a;BIO&#xff08;Blocking I/O&#xff0c;阻塞 I/O&#xff09;和 NIO&#xff08;Non-blocking I/O&#xff0c;非阻塞 I/O&#xff09;。它们都是 Java 中用于处理 I/O 操作的不同编程模型。 一、介…...

YOLOv5实战记录05 Pyside6可视化界面

个人打卡&#xff0c;慎看。 指路大佬&#xff1a;【手把手带你实战YOLOv5-入门篇】YOLOv5 Pyside6可视化界面_哔哩哔哩_bilibili 零、虚拟环境迁移路径后pip报错解决 yolov5-master文件夹我换位置后&#xff0c;无法pip install了。解决如下&#xff1a; activate.bat中修改…...

HTML5.Canvas简介

1. Canvas.getContext getContext(“2d”)是Canvas元素的方法&#xff0c;用于获取一个用于绘制2D图形的绘图上下文对象。在给定的代码中&#xff0c;首先通过getElementById方法获取id为"myCanvas"的Canvas元素&#xff0c;然后使用getContext(“2d”)方法获取该Ca…...

excel统计分析——多项式回归

参考资料&#xff1a;生物统计学 多项式回归属于单变量曲线回归&#xff0c;但其形式和求解方法与多元线性回归相似。多项式回归的数学模型为&#xff1a; 令&#xff0c;&#xff0c;&#xff0c;&#xff0c;则 由于X不可逆&#xff0c;两边同时乘以X得&#xff0c;&#xff…...

SQLyog连接数据库8.0版本解析错误问题解决方案

问题描述&#xff1a; 解决方案&#xff1a; alter userrootlocalhostidentified with mysql_native_password by 密码; 再次连接就可以了。...

【数据库】SQL简介

SQL&#xff08;Structured Query Language&#xff0c;结构化查询语言&#xff09;是一种用于管理关系型数据库管理系统&#xff08;RDBMS&#xff09;的标准化语言。它用于访问和操作数据库中的数据&#xff0c;执行各种任务&#xff0c;如插入、更新、删除和检索数据&#x…...

AWS入门实践-利用S3构建一个静态网站

使用Amazon S3托管静态网站是一个流行的选择&#xff0c;因为它简单、成本效益高&#xff0c;并且易于维护。静态网站由不含服务器端脚本的文件组成&#xff0c;如HTML、CSS和JavaScript文件。下面是使用S3托管静态网站的操作步骤&#xff1a; 如果大家没有AWS免费账号&#x…...

使用Linux strace追踪系统调用: 一个详细指南

使用Linux strace追踪系统调用: 一个详细指南 Linux strace是一个强大的命令行工具&#xff0c;用于监视和调试进程中发生的系统调用和信号。它对于系统管理员和开发人员来说是理解程序行为和解决问题的重要工具。 什么是strace&#xff1f; strace是一种跟踪运行中的进程执…...

python 笔记

文章目录 pdbpdb开始调试pythonpdb设置断点单步执行进入到函数的内部执行到下一个断点或程序结束调用栈查看命令查看当前函数调用堆栈向上一层函数查看调用堆栈查看源代码 importimport 用法 numpy导入numpy模块numpy常用函数np.argmaxnp.sum range生成连续序列生成不连续序列 …...

软考 系统架构设计师系列知识点之数据库基本概念(4)

接前一篇文章&#xff1a;软考 系统架构设计师系列知识点之数据库基本概念&#xff08;3&#xff09; 所属章节&#xff1a; 第6章. 数据库设计基础知识 第1节 数据库基本概念 6.1.3 数据库管理系统 DBMS&#xff08;DataBase Management System&#xff0c;数据库管理系统&am…...

东莞常平疫情/深圳品牌seo

1个月前&#xff0c;和Annie MSN聊天时&#xff0c;Annie曾竭力劝说我要买就买个带3G功能的iPAD&#xff0c;她以过来者的身份说&#xff0c;iPAD没有3G&#xff0c;功能损失一大半&#xff01;我则斩钉截铁地说&#xff0c;我不要3G版&#xff0c;Wifi于我就足够了。当时主要还…...

互联网网站建设哪里好/网络软文推广网站

---- 人们在使用SQL时往往会陷入一个误区&#xff0c;即太关注于所得的结果是否正确&#xff0c;而忽略了不同的实现方法之间可能存在的性能差异&#xff0c;这种性能差异在大型的或是复杂的数据库环境中&#xff08;如联机事务处理OLTP或决策支持系统DSS&#xff09;中表现得尤…...

西安企业网站建设代理机构/邯郸seo

优平均差稳定性简单选择排序O(n2)O(n2)O(n2) 直接插入排序O(n)O(n2)O(n2) √冒泡排序O(n)O(n2)O(n2) √希尔排序O(nlog2n)O(nlogn)O(nlog2n) 快速排序O(nlogn)O(nlogn)O(n2) 堆排序O(nlogn)O(nlogn)O(nlogn) 归并排序O(nlogn)O(nlogn)O(nlogn) √计数排序…...

杭州集团网站建设/google下载安卓版下载

五、Tensor-train分解 1. 量子态与量子算符 我们知道&#xff0c;量子的状态用态矢 ∣φ⟩|\varphi\rangle∣φ⟩ 来表示&#xff0c;可以表示为基态的线性组合的系数构成的列向量&#xff0c;算符表示对态矢的操作&#xff0c;可以通过矩阵来表示。 给定基矢&#xff0c;确定量…...

民宅挂在民宿网站上 保洁谁做/百度关键词排名怎么查

这是一个客户找我定制开发的&#xff0c;该客要开一个展会&#xff0c;需要在入场时吸粉&#xff0c;让想进展会的用户扫码关注公众号&#xff0c;然后点报名&#xff0c;提交姓名电话后&#xff0c;生成入场券&#xff0c;然后管理员审核是否同意入场&#xff1b; 管理员可以扫…...

网站建设和优化排名/百度一下首页手机版

在当今的移动盛世&#xff0c;谈论APP“生存”话题未免太过沉重。但面对百万级移动应用大军所产生的激烈竞争&#xff0c;且保证“立而不倒”&#xff0c;这样的探讨就显得格外重要了。 主打“价值牌”才能“一条龙” 有这样一组数据&#xff0c;在我国&#xff0c;APP只被打开…...