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

Linux软硬链接和动静态库

软硬链接和动静态库

本文已收录至《Linux知识与编程》专栏!
作者:ARMCSKGT
演示环境:CentOS 7

在这里插入图片描述


软硬链接和动静态库

  • 前言
  • 正文
    • 软硬链接
      • 原理
      • 使用
    • 文件时间
    • 动静态库
      • 库介绍
      • 静态库
        • 静态库制作
        • 静态库的使用
        • 关于静态链接
      • 动态库
        • 动态库制作
        • 动态库的使用
        • 关于动态链接
      • 补充
  • 最后


前言

当我们安装一款软件成功后,桌面会多一个图标,如果我们点击图标就能启动软件,但那个图标就是软件本身吗?显然不是!图标只是软件启动程序的一个快捷方式,在Linux中可以通过软硬链接来创建类似于Windows下的软件快捷方式,Windows下创建快捷方式一般相当于Linux中的软连接;当Windows中的一个软件启动之后会加载各种文件,一般我们看到的软件启动程序都很小,但是软件安装包却很大,例如游戏,其实软件中大部分都是库文件,关于Linux下的库,本节将会详细为您介绍!
软连接与库文件


正文

软硬链接

关于软硬链接,其中涉及Linux文件系统的知识,如果有疑问,请先移步:Linux文件系统概述


原理


软链接
软链接又称为符号链接,软链接是一个单独的文件,启动这个软链接程序会跳转启动这个软链接指向的程序,既然是一个单独的文件,那么软链接文件就拥有独立的inode和文件属性,软链接的主要存储内容是源文件的地址,所以软连接一般很小且依赖源文件!
Windows的软链接文件
因为软连接非常依赖源文件,所以源文件一旦不存在或被源文件路径出错,再次启动该软链接(快捷方式)则会出现 No such file or directory 的错误提示,表示系统没有找到对应文件!

当我们删除软链接文件时,并不会对源文件产生任何影响,就像我们删除Windows桌面上的快捷方式并不是清除了该软件一样,想删除该软件必须删除该软件所在的安装目录!


硬链接
硬链接与软链接不同,硬链接没有独立的inode和文件属性,其只是在目录中创建了与源文件inode和硬链接名的映射关系,并在源文件的文件属性中引用计数进行+1,表示增加了一个硬链接!
硬链接
当我们删除一个硬链接时,文件系统会判断该链接的inode源文件ret_count计数是否为0,如果减去1后引用为0则删除该文件,否则只是删除该目录下的一个硬链接映射关系且源文件引用计数-1,所以删除硬链接文件,只有删除最后一个硬链接才是真正删除文件,否则也不会对源文件产生影响!

所以,硬链接并不在意源文件,因为只要硬链接存在,文件就存在,而软链接的源文件被删除则软链接失效!

普通文件可以建立硬链接和软链接,但是目录只能建立软链接!
当我们新建一个文件时,其默认硬链接数为1,而目录的默认硬链接数为2
目录和普通文件硬链接
为什么新目录的硬链接数为2? 因为新目录与父级目录建立了硬链接

在Linux系统中, . 表示本目录,**. .**表示上级目录!

所以在父级目录下,每创建一个新目录,其硬链接数就会+1,因为新目录与父级目录构建的新的硬链接关系,但是Linux系统不允许用户手动为目录创建硬链接,因为这样会破坏文件系统的树结构,严重时可能会变成图,使得文件系统崩溃!
文件系统的树结构
硬链接就像是浅拷贝,只拷贝了inode。


使用


生成软链接文件:

$ ln -s 源文件路径 软链接文件名

软链接演示
注意:可以对目录进行软链接,其方式与普通文件进行软链接方式相同!



生成硬链接文件:

$ ln 源文件路径 软链接文件名

硬链接演示

虽然软硬链接在使用上没有差别,但是底层差别还是非常大的!
软链接硬链接文件

取消链接:

  • 删除链接文件
$ rm 链接文件
  • unlink取消链接
$ unlink 链接文件

取消链接
注意:普通文件的首个标识符为 -,软链接文件标识符为 l,而硬链接本质上是源文件的别名,所以也是普通文件 -
文件类型标识


文件时间


每一个文件从创建之日起就有三个时间(简称为 ACM 时间):

  • 访问时间 Access :最后一次查看内容的时间,如何判定取决于系统
  • 修改属性时间 Change:最后一次修改文件属性的时间
  • 修改内容时间 Modify:最后一次修改文件内容的时间

注意: 因为modify是文件属性,modify修改了change也会修改;更改文件内容与查看文件内容不一样,区别于access和modify,查看文件改变access,修改文件改变modify,Linux系统并非每次查看都会改变文件的access时间(因为修改access涉及文件属性的修改需要读取硬盘),有一定的策略,这样可以减少与硬盘的交涉提高效率。


我们可以通过 stat 命令查看文件属性和ACM时间:

$ stat 文件名

stat指令


动静态库


库介绍

原来在学习C语言时,写一下学校课程设计可能会需要函数的声明和定义进行分离,这样可以让代码显得不凌乱!
函数声明与定义分离
其实图中的test.cpp就可以充当一个C/C++的函数库,但是我们在使用时需要结合头文件test.h一起使用!


但是在实际的项目开发过程中,一个保密的项目是不能透露库中的源代码的,我们只想留下 头文件 声明函数接口,而具体实现放在一个保密的库中(别人可以使用,但是无法获取函数实现),此时我们就需要引入动静态库了!

说明: 一般系统已经预装了C/C++头文件和动态库文件,头文件提供方法说明,库提供方法实现,头和库是有对应关系的,要组合在一起使用;头文件是在预处理阶段就引入的,链接的本质其实就是链接库;引入库文件一方面是为了提高开发效率(代码复用性等),另一方面可以保密!


无论是在Linux系统中还是Windows系统中,都存在库,分为动态库静态库,虽然不同环境下的后缀有所不同,但其工作原理是一致的!

  • Linux 系统中:.a 后缀为静态库,.so 后缀为动态库
  • Windows 系统中:.lib 后缀为静态库,.dll 后缀为动态库

在Linux系统中,库命名一般为:libstdc++.so.6,去掉前缀 lib 和后缀 .so.6 ,剩下的就是库名 stdc++

我们可以使用命令查看Linux环境中的库文件:

# 查看C库
$ find /usr/lib64/libc*
# 查看C++库
$ find /usr/lib64/libstdc*
# 查看所有库
$ find /usr/lib64/lib

Linux环境中的库文件
该图只截取了一部分,实际上有很多库!

在我们写C/C++程序时,离不开库函数,比如我们使用的各种STL容器,库中只会提供给我们头文件开放接口进行使用,并不会让我们看到具体实现,其具体实现已经打包成库(二进制文件),在平时使用时,编译器默认使用动态库而非静态库,动态库在日常使用具有较大优势

如果我们想指定使用静态库编译,在gcc/g++下,只需要加上 -static 选项即可,但是前提是Linux环境中已经安装C/C++静态库,一般服务器和虚拟机是没有安装的!

C/C++静态库的安装(非root用户需要sudo提权):

# 安装C静态库
yum install -y glibc-static
# 安装C++静态库
yum install -y libstdc++-static

动静态库比较:

区别静态库动态库
空间大小占用空间较大占用空间小
调用方式函数实现在程序中,直接在程序中执行通过地址转到动态库中执行动代码
加载速度库函数加载到程序中,空间占用大多个程序共享一个已加载的动态库,空间占用小
依赖性直接在程序中运行依赖于动态库

补充: 动态库是在函数调用出留下地址链接,在调用该函数时转到内存中的动态库在指定的函数位置执行代码;而静态库是将函数实现直接拷贝到调用出,运行时直接执行!

简言之,如果没有库文件,那么你在开发时,需要自己手动将 printf/cout 等高频函数编写出来,因此库文件可以提高我们的开发效率,比如 Python 中就有很多现成的库函数可以使用,效率很高!

一般库分为三种:

  • 第一方库:语言自带的库
  • 第二方库:操作系统提供的库
  • 第三方库:我们自己制作的库或网上下载的库

静态库


静态库制作

准备库文件和头文件

add.hpp

#pragma onceint add(int a,int b);

add.cpp

#include "add.hpp"int add(int a,int b) { return a+b; }

sub.hpp

#pragma onceint sub(int a,int b);

add.cpp

#include "sub.hpp"int sub(int a,int b) { return a-b; }

main.cpp

#include <iostream>
#include "add.hpp"
#include "sub.hpp"
using namespace std;int main()
{cout<<add(1,2)<<endl;cout<<sub(1,2)<<endl;return 0;
}

编译链接形成二进制程序:

$ g++ main.cpp add.cpp sub.cpp -o exe -std=c++11

注意:声明与定义分离的情况下,需要指明链接的函数实现文件
执行结果

接下来开始打包成静态库,主要分为两步:

  • 1.将源文件进行 预处理->编译->汇编,生成可链接的二进制 .o 文件
$ g++ -c add.cpp sub.cpp

在这里插入图片描述
执行完毕后生成与文件名相同的 .o 二进制链接文件

  • 2.通过 ar指令 将 .o 文件打包为静态库
#格式:ar -rc { lib静态库名.a } {链接文件1.o 链接文件2.o ...}
$ ar -rc libmymath.a add.o sub.o
# 也可以简写为:ar -rc libmymath.a *.o

注意:实际的静态库名为 mymath 但是gcc/g++编译器会识别静态库自动去掉头(lib)尾(.a),按照规范我们必须这样写!
生成静态库文件
此时就成功生成了静态库文件!


ar指令除了可以打包链接文件成为库文件,还可以查看库文件中的打包内容:

$ ar -tv {静态库文件.o}

查看静态库打包内容

静态库的使用

我们自己指针的库是第三方库,在使用上区别与第一方和第二方库区别很大!
此时如果我们直接编译程序,是无法编译的!

我们将上面使用和生成的文件进行规整:
文件规整
将头文件放在_hpp目录,库文件放在lib,链接文件放在_o,实现文件放在_cpp,留下main.cpp在本目录下,这样在本目录下就既没有头文件也没有实现文件了,此时我们进行静态编译!


1.直接使用静态库

# 格式:g++ 代码文件.cpp  -I 头文件夹路径 -L 库文件夹路径 -l 静态库名(去掉头尾)
$ g++ main.cpp -o static_exe  -I ./_hpp -L ./lib -l mymath -static #静态链接
$ g++ main.cpp -o exe  -I ./_hpp -L ./lib -l mymath #动静混合
# gcc使用方法与此相同

运行演示
使用第三方库与使用标准库和系统库不同,使用标准库和系统库都是系统级的,gcc/g++ 默认找的就是 stdc/stdc++ 库,而第三方库则需要我们自己指定!


2.将头文件和静态库文件安装至系统库下
Linux系统C/C++头文件路径:/usr/include/
Linux系统库路径:/lib64/

# 注意:非root用户需要sudo提权
$ cp ./_hpp/*.hpp /usr/include/
$ cp ./lib/*.a /lib64/

将库和头文件安装到系统目录下后,只需要指定库名即可完成编译链接!

$ g++ main.cpp -o exe -l mymath #动静混合
$ g++ main.cpp -o static_exe -l mymath -static #静态链接


注意:这里极其不提倡这种私自安装外部库的方式,将自己写的文件安装到系统目录下是一件危险的事(导致系统环境被污染),如果不得已,用完后记得手动删除!

关于静态链接

静态链接,是在链接时将调用函数处的函数调用替换为函数执行代码(二进制代码),可执行程序从根本上脱离了库的限制,在同系统的机器上无论是否有静态库都可以运行,不依赖任何静态库!

静态库所体现的优点是运行比较快,但静态链接形成的可执行程序本身就有静态库中对应方法的实现(将代码拷贝到可执行程序中),静态链接的程序,非常占用资源,内存中会程序多个重复的代码(可执行程序体积变大加载占用内存),也占用磁盘资源,如果是给用户用的软件那么下载周期就会变长,占用网络资源!

注意:如果要使用静态链接需要加上 -static 否则编译器将使用静态库进行动态库和静态库的混合链接!


动态库


动态库制作

我们准备与静态库制作相同的五个文件

在这里插入图片描述
打包为动态库分为两步:

  • 1.编译源文件,生成二进制可链接文件.o同时形成与位置无关码
# 格式:gcc -c -fPIC {实现文件.cpp}
$ g++ -c -fPIC add.cpp sub.cpp
# gcc 使用方式与g++相同


同样的,会形成 .o 链接文件!

说明:fPIC这个选项是形成.o文件同时形成与位置无关码,动态库中里面的代码地址排布与静态库是有区别的,动态库经常使用,所以gcc/g++自带打包动态库功能。

  • 2.打包链接文件形成动态库
# 格式:g++ -shared { 链接文件.o } -o { libmymath.so }
g++ -o libmymath.so *.o -shared
# gcc 使用方式与此相同

动态库生成
说明:shared表示形成(打包成)动态库或共享文件

动态库的使用

同样的,我们先规整文件到不同的文件夹


我们使用静态库的方法去编译可执行程序:

$ g++ main.cpp -o exe -I ./_hpp -L ./lib -l mymath

执行情况
之所以会运行失败,是因为当前只告诉了编译器动态库的位置,没有告诉 OS!

出现这种情况,可以使用 ldd 指令查看程序的链接情况:

$ ldd 可执行程序

ldd指令运行结果
动态库处,显示状态为没有链接,未发现动态库!

这也说明,我们不能盲目进行链接,在此之前我们需要让操作系统知道库的位置,有三种方法:

  • 1.修改临时环境变量: 添加动态库路径至 LD_LIBRARY_PATH 环境变量中;因为环境变量 LD_LIBRARY_PATH 是程序在进行动态库查找时的默认搜索路径。
$ export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:/动态库目录详细(绝对)路径/

链接情况
注意: 更改环境变量只是临时方案,重新登录bash后就失效了,需要重新配置

  • 2.将动态库的软链接文件存入系统目录中

    我们将动态库建立软链接放入系统库目录中(普通用户需要sudo提权)
# ln -s /动态库绝对路径/ /lib64/动态库名称(与软链接的动态库名称相同)$ ln -s /home/ARMCSKGT/演示文件夹/lib/libmymath.so /lib64/libmymath.so


注意: 创建软连接文件时,需要使用绝对路径;这种方式的修改是永久有效的,但是我们不建议使用,如果非必要建议用后删除,避免冲突和污染系统环境。

  • 3.更改配置文件中的信息
    系统的第三个动态库查找路径就是前往动态库配置目录的各配置文件提供的路径中查找,我们可以写一个自己配置文件,里面写入动态库的路径,放入该目录中!
$ touch mylib.conf  #创建一个配置文件
$ echo /home/ARMCSKGT/演示文件夹/lib/ > mylib.conf #将动态库绝对路径写入配置文件
$ mv mylib.conf /etc/ld.so.conf.d/ #将配置文件放入系统目录/etc/ld.so.conf.d/中
$ ldconfig #重新加载系统配置文件

说明: mv和ldconfig操作在普通用户操作下需要sudo提权

注意: 这种方式的修改也是永久有效的,如果非必要建议用后删除,避免冲突和污染系统环境。

关于动态链接

动态库的链接:将可执行程序中的外部符号替换为库中的具体地址,在程序执行时直接将库地址加载到内存中,只要我们把库加载到内存,映射到进程的地址空间中后,我们的代码执行库中的方法,就依旧还是在自己的地址空间内进行函数跳转,当库因为程序调用已经在内存中,另一个程序使用时就直接在页表中映射然后在共享空间中调用即可!

动态库的方法只需要在内存中存在一份就可以被所有进程使用了,库的加载也不一定是全部加载到内存,使用什么加载什么就行,具体根据操作系统的策略就行操作。

程序在链接动态库函数时,是通过 动态库起始地址 + 所链接函数偏移量 的方式进行链接访问的,而这个偏移量就是 fPIC 与位置无关码!

地址就两类:绝对编址 and 相对编制

静态链接时,将可链接的二进制文件加载至程序中,直接通过 绝对地址 进行链接,如果函数被调用了多次,就会导致代码冗余等问题。
动态链接采用 相对地址 的方式进行链接,同一个函数的 动态库起始地址 + 所链接函数偏移量 值相同,代码只需要加载一份,并且可以任意位置进行函数调用(与位置无关)。

动态库必定面临一个问题:不同的进程,运行程度不同,需要使用的第三方库不同,注定了每一个进程的共享空间中的空闲位置是不确定的

动态库中的地址,绝对不能确定,去使用绝对编址,动态库中的所有地址都是偏移量,默认从0地址开始,当一个库真正被映射到地址空间时,他的起始地址才能真正确定,动态库在进程的地址空间中随便加载,与我们加载到地址空间的什么位置毫无关系!


补充

当同时存在动态库和静态库时,编译器默认采用动态库!

如果我们想指定生成静态库程序,只需要加上 -static 选项即可:

$ g++ [代码文件.cpp] -static #如果是第三方库需要指定头文件,库路径和库名称

如果只提供静态库,但编译时不加-static,编译时会将静态库进行静态链接(结合具体的情况)(将可以动态链接的库动态链接,然后将不能动态链接的静态库中代码拷贝到文件中),可以动态链接的库进行动态链接!

三种链接方式对比
静态链接生成的程序比动态链接大得多,并且内含静态库的动态链接程序,也比纯粹的动态链接程序大,说明程序不是 非静即动,可以同时使用动态库与静态库!


最后

以上就是 【Linux软硬链接和动静态库】 的全部内容了,本节我们结束了如同快捷方式一样的软硬链接,让我们可以对目标建立链接快速访问,同时学习了程序的运行需要库的加持,动静态库的区别,学习了制作库,最后介绍了库的链接原理,相信本次的介绍可以帮助各位开发者!

本次 <Linux软硬链接和动静态库> 就先介绍到这里啦,希望能够尽可能帮助到大家。

如果文章中有瑕疵,还请各位大佬细心点评和留言,我将立即修补错误,谢谢!
结尾

🌟其他文章阅读推荐🌟
Linux<文件系统概述> -CSDN博客
Linux<重定向和缓冲区理解> -CSDN博客
Linux<文件理解和系统调用> -CSDN博客
Linux<进程控制> -CSDN博客
Linux<进程地址空间> -CSDN博客
🌹欢迎读者多多浏览多多支持!🌹

相关文章:

Linux软硬链接和动静态库

本文已收录至《Linux知识与编程》专栏&#xff01; 作者&#xff1a;ARMCSKGT 演示环境&#xff1a;CentOS 7 软硬链接和动静态库 前言正文软硬链接原理使用 文件时间动静态库库介绍静态库静态库制作静态库的使用关于静态链接 动态库动态库制作动态库的使用关于动态链接 补充 最…...

Linux shell编程学习笔记6:查看和设置变量的常用命令

上节我们介绍了变量的变量命名规则、变量类型、使用变量时要注意的事项&#xff0c;今天我们学习一下查看和设置变量的一些常用命令&#xff0c;包括变量的提升&#xff0c;有些命令在之前的实例中已经使用过了。 一、 echo &#xff1a;查看变量的值 语法格式&#xff1a;ech…...

leetcode 416.分割等和子集

416. 分割等和子集 给你一个 只包含正整数 的 非空 数组 nums 。请你判断是否可以将这个数组分割成两个子集&#xff0c;使得两个子集的元素和相等。 示例 1&#xff1a; 输入&#xff1a;nums [1,5,11,5] 输出&#xff1a;true 解释&#xff1a;数组可以分割成 [1, 5, 5] 和…...

Java基于SSM+Vue的平时成绩管理系统

末尾获取源码 开发语言&#xff1a;Java Java开发工具&#xff1a;JDK1.8 后端框架&#xff1a;SSM 前端&#xff1a;采用Vue技术开发 数据库&#xff1a;MySQL5.7和Navicat管理工具结合 服务器&#xff1a;Tomcat8.5 开发软件&#xff1a;IDEA / Eclipse 是否Maven项目&#x…...

flutter开发实战-webview插件flutter_inappwebview使用

flutter开发实战-webview插件flutter_inappwebview使用 在开发过程中&#xff0c;经常遇到需要使用WebView&#xff0c;Webview需要调用原生的插件来实现。常见的flutter的webview插件是webview_flutter&#xff0c;flutter_inappwebview。之前整理了一下webview_flutter&…...

Selenium 浏览器坐标转桌面坐标

背景&#xff1a; 做图表自动化项目需要做拖拽操作&#xff0c;但是selenium提供的拖拽API无效&#xff0c;因此借用pyautogui实现拖拽&#xff0c;但是pyautogui的拖拽是基于Windows桌面坐标实现的&#xff0c;另外浏览器中的坐标与windows桌面坐标并不是一比一对应的关系&am…...

1.6.C++项目:仿muduo库实现并发服务器之channel模块的设计

项目完整版在&#xff1a; 文章目录 一、channel模块&#xff1a;事件管理Channel类实现二、提供的功能三、实现思想&#xff08;一&#xff09;功能&#xff08;二&#xff09;意义&#xff08;三&#xff09;功能设计 四、代码&#xff08;一&#xff09;框架&#xff08;二…...

Redis代替session 实现登录流程

Redis代替session 实现登录流程 如果使用String&#xff0c;他的value&#xff0c;用多占用一点空间&#xff0c;如果使用哈希&#xff0c;则他的value中只会存储他数据本身&#xff0c;如果不是特别在意内存&#xff0c;其实使用String就可以 设计key的具体细节 在设计这个k…...

理解C++强制类型转换

理解C强制类型转换 文章目录 理解C强制类型转换理解C强制转换运算符1 static_cast1.1. static_cast用于内置数据类型之间的转换1.2 用于指针之间的转换 1.3 用于基类与派生类之间的转换2. const_cast2.1示例12.2 示例2——this指针 3.reinterpret_cast4.dynamic_cast C认为C风格…...

《TCP/IP网络编程》代码实现

文章目录 1. 项目说明1.1 项目特点2. 文件说明2.1 脚本文件2.1.1 `TCP_IP.sln`2.1.2 `xmake.lua`2.1.2.1 编译说明2.1.2.2 运行说明2.1.3 章节说明项目代码已经开源在github上! 微信公众号文章同步发表! 1. 项目说明 根据《TCP/IP网络编程》书籍学习,对其中的代码进行整理,…...

【Python】如何使用PyInstaller打包自己写好的代码

使用PyInstaller打包自己写好的代码 零、需求 最近接到一个小单&#xff0c;需要批量修改文档内容&#xff0c;用Python做好后要打包成exe程序给客户的Win7电脑使用&#xff0c;此时需要用到PyInstaller打包自己的代码&#xff0c;想到还要有给用户试用的需求&#xff0c;所以…...

Java 线程的调度与时间片

&#x1f648;作者简介&#xff1a;练习时长两年半的Java up主 &#x1f649;个人主页&#xff1a;程序员老茶 &#x1f64a; ps:点赞&#x1f44d;是免费的&#xff0c;却可以让写博客的作者开兴好久好久&#x1f60e; &#x1f4da;系列专栏&#xff1a;Java全栈&#xff0c;…...

Java项目-文件搜索工具

目录 项目背景 项目效果 SQLite的下载安装 使用JDBC操作SQLite 第三方库pinyin4j pinyin4j的具体使用 封装pinyin4j 数据库的设计 创建实体类 实现DBUtil 封装FileDao 设计scan方法 多线程扫描 周期性扫描 控制台版本的客户端 图形化界面 设计图形化界面 项目…...

记录开发中遇到关于MySQL的一些问题-MySQL版

本篇文章是记录开发中遇到关于MySQL的一些问题&#xff1a; 希望在这篇文章也能够找到你正在查找的问题&#xff0c;解决问题 Good Luck ! 关于Id 的一些问题 数据库并没有直接写SQL&#xff0c;是通过使用IDEA 同一个公司下的数据库软件生成的&#xff08;DataGrip&#xf…...

2023-10-06 LeetCode每日一题(买卖股票的最佳时机含手续费)

2023-10-06每日一题 一、题目编号 714. 买卖股票的最佳时机含手续费二、题目链接 点击跳转到题目位置 三、题目描述 给定一个整数数组 prices&#xff0c;其中 prices[i]表示第 i 天的股票价格 &#xff1b;整数 fee 代表了交易股票的手续费用。 你可以无限次地完成交易&…...

openGauss学习笔记-91 openGauss 数据库管理-内存优化表MOT管理-内存表特性-使用MOT-MOT使用MOT外部支持工具

文章目录 openGauss学习笔记-91 openGauss 数据库管理-内存优化表MOT管理-内存表特性-使用MOT-MOT使用MOT外部支持工具91.1 gs_ctl&#xff08;全量和增量&#xff09;91.2 gs_basebackup91.3 gs_dump91.4 gs_restore openGauss学习笔记-91 openGauss 数据库管理-内存优化表MOT…...

PostgreSQL快速入门

PostgreSQL快速入门&#xff1a;轻松掌握强大的开源数据库 PostgreSQL&#xff08;简称Postgres&#xff09;是一款强大、可定制且免费的开源关系型数据库管理系统&#xff08;RDBMS&#xff09;。它以其高级功能、可扩展性和安全性而著称&#xff0c;被广泛用于各种规模的项目…...

MATLAB:线性系统的建模与仿真(含完整程序)

目录 前言实验内容一、先看作业题目要求二、作业正文Modeling LTI systemsEstablish model1.tf(sys2)2. tf(sys3)3.zpk(sys1)4. zpk(sys3)5. ss(sys1)6. ss(sys2)7.[num,den] tfdata(sys1)8.[num,den] tfdata(sys2)9.[num,den] tfdata(sys3)10.[num,den] tfdata(sys1,’v’…...

mycat实现mysql读写分离

架构图&#xff1a; 视频地址...

【C++】STL详解(十一)—— unordered_set、unordered_map的介绍及使用

​ ​&#x1f4dd;个人主页&#xff1a;Sherry的成长之路 &#x1f3e0;学习社区&#xff1a;Sherry的成长之路&#xff08;个人社区&#xff09; &#x1f4d6;专栏链接&#xff1a;C学习 &#x1f3af;长路漫漫浩浩&#xff0c;万事皆有期待 上一篇博客&#xff1a;【C】STL…...

【C语言】动态通讯录(超详细)

通讯录是一个可以很好锻炼我们对结构体的使用&#xff0c;加深对结构体的理解&#xff0c;在为以后学习数据结构打下结实的基础 这里我们想设计一个有添加联系人&#xff0c;删除联系人&#xff0c;查找联系人&#xff0c;修改联系人&#xff0c;展示联系人&#xff0c;排序这几…...

Mac下docker安装MySQL8.0.34

学习并记录一下如何用docker部署MySQL 在Docker中搜索并下载MySQL8.0.x的最新版本 下载好后&#xff0c;在Images中就可以看到MySQL的镜像了 通过下面的命令也可以查看docker images启动镜像&#xff0c;使用下面的命令就可以启动镜像了docker run -itd --name mysql8.0.34 -…...

基于python编写的excel表格数据标记的exe文件

目录 一、需求&#xff1a; 二、思路&#xff1a; 三、工具 四、设计过程 &#xff08;一&#xff09;根据需要导入相关的图形界面库 &#xff08;二&#xff09;创建图形窗口 &#xff08;三&#xff09;标签设计 &#xff08;四&#xff09;方法按钮设计 &#xff0…...

acwing算法基础之基础算法--高精度加法算法

目录 1 知识点2 模板 1 知识点 大整数 大整数&#xff0c;它们的长度都为 1 0 6 10^6 106。大整数是指长度为 1 0 6 10^6 106的整数。 大整数 - 大整数 大整数 * 小整数 大整数 / 小整数 把大整数存储到向量中&#xff0c;需要考虑高位在前还是低位在前&#xff0c;低位在前…...

openGauss学习笔记-84 openGauss 数据库管理-内存优化表MOT管理-内存表特性-MOT部署服务器优化:x86

文章目录 openGauss学习笔记-84 openGauss 数据库管理-内存优化表MOT管理-内存表特性-MOT部署服务器优化&#xff1a;x8684.1 BIOS84.2 操作系统环境设置84.3 网络 openGauss学习笔记-84 openGauss 数据库管理-内存优化表MOT管理-内存表特性-MOT部署服务器优化&#xff1a;x86 …...

二分查找:34. 在排序数组中查找元素的第一个和最后一个位置

个人主页 &#xff1a; 个人主页 个人专栏 &#xff1a; 《数据结构》 《C语言》《C》《算法》 文章目录 前言一、题目解析二、解题思路1. 暴力查找2. 一次二分查找 部分遍历3. 两次二分查找分别查找左右端点1.查找区间左端点2. 查找区间右端点 三、代码实现总结 前言 本篇文…...

javaee ssm框架项目整合thymeleaf2.0 更多thymeleaf标签用法 项目结构图

创建ssmthymeleaf项目 创建ssmthymeleaf项目参考此文 thymeleaf更多常用标签 <!DOCTYPE html> <html lang"en" xmlns:th"http://www.thymeleaf.org"> <head><meta charset"UTF-8"><title>Title</title> …...

lv7 嵌入式开发-网络编程开发 11 TCP管理与UDP协议

目录 1 TCP管理 1.1 三次握手 1.2 四次挥手 1.3 保活计时器 2 wireshark安装及实验 3.1 icmp协议抓包演示 3.2 tcp协议抓包演示 3 UDP协议 3.1 UDP 的主要特点&#xff1a; 4 练习 1 TCP管理 1.1 三次握手 TCP 建立连接的过程叫做握手。 采用三报文握手&#xff1…...

overleaf在线编辑工具使用教程

文章目录 1 用 orcid注册overleaf获取模板2 使用模板 1 用 orcid注册overleaf获取模板 通常来说&#xff0c;在期刊投稿网站information for author中找template 。下载压缩包后上传到over leaf中。 加入找不到官方模板&#xff0c;用overleaf中的 2 使用模板 .bib文件&…...

Python基础复习【第一弹】【黑马】

本篇是观看b站黑马视频所做的笔记第一弹&#xff0c;为1-98节。 b站-黑马Python # 1.Hello World print("Hello World")# 2.字面量 在代码中&#xff0c;被写下来固定的值# 3.字符串 print("python")# 4.单行注释 # 多行注释""" "&q…...

wordpress修改登陆/seo查询网站是什么

1、db2可以通过SYSIBM.SYSDUMMY1、SYSIBM.DUAL获取寄存器中的值&#xff0c;也可以通过VALUES关键字获取寄存器中的值。SELECT HELLO DB2 FROM SYSIBM.SYSDUMMY1;--HELLO DB2SELECT HELLO DB2 FROM SYSIBM.DUAL;--HELLO DB2VALUES HELLO DB2;--HELLO DB22、CURRENT DATE获取当前…...

网络科技网站建设/互联网营销方式

在上一篇博客中简介了构造器基础层面的知识构造器(一)&#xff0c;以下我们深入的学习类的构造器应用。在Swift中类一共同拥有两种构造器&#xff1a; 指定构造器便利构造器什么是指定构造器&#xff0c;有什么作用&#xff1f; 我个人的理解为在类中没有加不论什么keyword的构…...

wordpress自带小工具栏/无人区在线观看高清1080

博客链接: http://codeshold.me/2017/02/interview_notes.html McDowell的《金领简历&#xff1a;敲开苹果、微软、谷歌的大门》第7章的个人总结和笔记。详细可参阅careercup.com 网站。 明白科技公司需要什么样的人 对技术的激情&#xff0c;对公司的激情&#xff0c;创意无限…...

大型电子商务网站建设/湖南关键词排名推广

我已经编写了这段代码&#xff0c;以便使用检查用户名和密码的bean和servlet从jsp登录。从mysql数据库。代码如下&#xff1a;index.jsp:/p>"http://www.w3.org/TR/html4/loose.dtd">body {background-color:#AFC7C7;padding: 0;margin: 0;}div.wrapper {margi…...

如何建设平台型的网站/百度经验悬赏任务平台

文章目录一、前言二、准备三、Parallels Desktop安装CentOS7四、CentOS7配置1、网络配置 -- 设置固定ip2、关闭防火墙3、关闭SELinux4、更新yum源5、安装ifconfig6、其它一、前言 本文将通过Parallels Desktop安装CentOS7 二、准备 Parallels Desktop下载安装 https://www.p…...

wordpress 5.2更新了什么意思/国外搜索引擎大全

这是悦乐书的第279次更新&#xff0c;第295篇原创01 看题和准备今天介绍的是LeetCode算法题中Easy级别的第147题(顺位题号是645)。集合S最初包含从1到n的数字。 但不幸的是&#xff0c;由于数据错误&#xff0c;集合中的一个数字被复制到集合中的另一个数字&#xff0c;这导致重…...