网络 tcp/ip
七层协议及每层作用
层 | 作用 |
---|---|
应用层 | 主要负责提供上层服务或应用的功能,比如http,smtp,snmp等。 |
表示层 | 对数据进行处理,以人可以阅读的方式进行展示 |
会话层 | 负责网络两端的通信连接的建立,发起并维护会话 tls,ssl,ldap,rpc |
传输层 | 对数据段分割排序,负责数据的传输,根据需要选择tcp udp |
网络层 | 负责地址的管理和路由的选择,对数据进行ip封装,形成数据包,ip,ICMP,VRRP,OSPF。路由器 |
数据链路层 | 负责数据的成帧,流量控制,重传控制。ARP,RARP。交换机,网卡。 |
物理层 | 电子信号转化为比特流,集线器 |
http 和 https 的区别:
无连接:服务器处理完客户的请求,并收到客户的应答后,即断开连接。
无状态:是指服务器不知道客户端是什么状态。
http:超文本传输协议,是一个基于请求与响应,基于tcpip的应用层协议,无状态,无连接通信使用明文、请求和响应不会对通信方进行确认、无法保护数据的完整性。
https:通过 ssl/tls 的ca证书建立全信道,加密数据包,提供对网站服务器的身份认证,同时保护交换数据的隐私与完整性,
http和https使用的是完全不同的连接方式,用的端口也不一样,前者是80,后者是443。
https的加密方式
Https不是应用层的新协议,而是Http通信接口用SSL和TLS来加强加密和认证机制。
- 对称加密:加密和解密都是同一个密匙。AES,DES
对称加密速度快,对称加密要将密钥暴露,和明文传输没区别。
弊端:服务器和浏览器之间传递密钥的过程被人监听,相当明文传输。
- 非对称加密:密钥成对出现,分为公钥和私钥,公钥加密需要私钥解密,私钥加密需要公钥解密。RSA,DSA
非对称加密速度慢,非对称加密将公钥暴露,供客户端加密,服务端使用私钥解密。
弊端:服务端只将公钥暴露,浏览器使用公钥对消息进行非对称加密,服务端用私钥解密。但是服务端向浏览器回复的时候,只能用私钥进行加密,浏览器只能用公钥解密。但是:公钥是所有人都知道的,所有人都可以读取服务端回复的消息来进行解密,所以解决不了服务端向浏览器传递消息。
可以采用对称加密和非对称加密结合的方式:
- 线性散列算法: MD5,SHA1,HMAC
http中的常见状态码
200 OK:表示从客户端发送给服务器的请求被正常处理并返回;
204 No Content:请求成功处理,但没有资源可以返回;
206 Patial Content:表示客户端进行了范围请求
301 Moved Permanently:永久性重定向,表示请求的资源被分配了新的URL
302 Found:临时性重定向,表示请求的资源被分配了新的URL,希望本次访问使用新的URL;
303 See Other:表示请求的资源被分配了新的URL,应使用GET方法定向获取请求的资源;
302与303的区别:后者明确表示客户端应当采用GET方式获取资源
304 Not Modified:表示客户端发送附带条件的请求时,服务器端允许访问资源,但是请求为满足条件的情况下返回改状态码;
307 Temporary Redirect:临时重定向,与303有着相同的含义,307准不会从POST变成GET;
400 Bad Request:表示请求报文中存在语法错误;
401 Unauthorized:未经许可,需要通过HTTP认证;
403 Forbidden:服务器拒绝该次访问(访问权限出现问题)
404 Not Found:表示服务器上无法找到请求的资源,
nginx中:
494:请求头太大
495:https证书错误
496:https 没有证书
497:http到https
498:取消
499:客户端关闭链接(服务器端处理的时间过长,客户端“不耐烦”了,断开了链接。)
499例子:nginx反代到一个永远打不开的后端,客户端请求超时,主动断开连接
500 Inter Server Error:表示服务器在执行请求时发生了错误,可能是web应用存在的bug或临时的错误
502 bad gateway 上有服务器错误或者解析失败
503 Server Unavailable:表示服务器暂时处于超负载或正在进行停机维护,无法处理请求;
504 gateway timeout: 响应超时
get和post的区别
浏览器输入一个网址访问网站都是GET请求,再FORM表单中,可以通过设置Method指定提交方式为GET或者POST提交方式,默认为GET提交方式。
1.post更安全(不会作为url的一部分,不会被缓存、保存在服务器日志、以及浏览器浏览记录中)
2.post发送的数据量更大(get有url长度限制)
3.post能发送更多的数据类型(get只能发送ASCII字符)
4.post比get慢 get的消耗是post的 2/3,因为第三次握手时,post只发送post头,而get发送get头和数据。
5.get会将数据缓存起来,而post不会,所以get通常用于静态数据
6 post不能进行管道化传输,管道化传输失败时可以重传,但是对于post这种改变服务器状态的请求是不适用的,比如在支付的时候。
udp 和 tcp的区别:
TCP面向连接;UDP是无连接的,即发送数据之前不需要建立连接
TCP提供可靠的服务。也就是说,通过TCP连接传送的数据,无差错,不丢失,不重复,且按序达;UDP尽最大努力交付,即不保证可靠交付
Tcp通过校验和,重传控制,序号标识,滑动窗口、确认应答实现可靠传输。如丢包时的重发控制,还可以对次序乱掉的分包进行顺序控制。
UDP具有较好的实时性,工作效率比TCP高,适用于对高速传输和实时性有较高的通信或广播通信。
每一条TCP连接只能是点到点的;UDP支持一对一,一对多,多对一和多对多的交互通信
TCP对系统资源要求较多,UDP对系统资源要求较少。
tcp:http,https,ftp,ssh,smtp.telnet 头部20位
udp: nfs,dns,dhcp,tftp 头部8位
ip:头部4位
场景:
tcp:文件传输
udp:语音通话,视频通话
滑动窗口
窗口是缓存的一部分,用来暂时存放字节流。
流量控制的目的:控制发送方数据发送速率,保证接收方来得及接收
窗口:发送者发送的连续字节序列的集合
滑动:发送的窗口可以随发送过程而变化。
为什么需要窗口:不必每一个段进行一次确认应答,而是以一个窗口的大小进行确认。减少往返时间,提高速度。(TCP在发送时其实是以字节为单位的)
ping使用的协议,丢包处理
使用3层网络层的 ICMP 协议,tcping可以ping端口
检测tcp udp端口是否可以通信
inux下 Netstat工具 简称NC,号称是网络工具中的“瑞士军刀”,今日一见果然名不虚传。
我们都知道检测TCP端口是否可通的命令是telnet,在windows和Linux都可以用,但telnet不能检测udp端口,今天给大家介绍的是Linux下 NC命令用于检测UDP端口是否可通。
Telnet 检测TCP端口
[root@apexsoft ~]# telnet 127.0.0.1 8906
Trying 127.0.0.1...
Connected to 127.0.0.1.
Escape character is '^]'.
^CConnection closed by foreign host.
NC 检测TCP端口
[root@apexsoft ~]# nc -vz 127.0.0.1 8906
Connection to 127.0.0.1 8906 port [tcp/*] succeeded!
NC 检测UDP端口
检测udp端口的时候不会立即返回测试结果,可能需要等待几秒钟
[root@apexsoft ~]# nc -uz 127.0.0.1 8907
Connection to 127.0.0.1 8907 port [udp/*] succeeded!
查看路由
当网络故障时或在分析某些问题时,需要查看linux设备到某个IP的路由信息。使用traceroute命令即可查看。
具体命令如下:
traceroute xxx.xxx.xxx.xxx
查看路由表:
netstat -rn
或者 route 命令
网关和路由的区别
网关是网络的进口和出口(网关还有其他功能,如协议翻译……),网关定义网络的边界。如果只是简单地连接两个网络,那么只需要网关就足够了。
路由器使用一系列算法决定网络间的最短路径。路由器使用静态路由或动态路由来决定网络间的最短路径,当网络比较多时,有多个路由器,就选择路由
ipv4和ipv6的区别
ipv4:
32位 4字节,有ARP协议,dns中使用 A 记录
ipv6:
128位16字节 体系结构更复杂,可用地址更多,无ARP协议,dns中使用 AAAA 记录,不支持 NAT地址转换。使用的DHCP服务支持和 ipv4 不同。
区别
linux
软链接和硬链接的区别
硬链接:用 ln 创建。1个inode号对应多个文件。多个文件名指向同一索引节点。
- 硬连接的作用是允许一个文件拥有多个有效路径名,这样用户就可以建立硬连接到重要文件,以防止“误删”的功能
软连接:用 ln -s 创建,软连接是一个普通文件,有自己独立的inode
- 删了这个软连接文件,那就等于不需要这个连接,和原来的存在的实体原文件没有任何关系
- 删除原来的文件,则相应的软连接不可用(cat那个软链接文件,则提示“没有该文件或目录“)
linux自动删除30天前的日志文件:
find /opt/backup/log/ -mtime +30 -name “*.log” -exec rm -rf {} ;
修改运行级别:
runlevel
vim /etc/inittab
防火墙:
将内部网络和外部网络隔离的网络安全系统,护内部/私有局域网免受外部攻击,并防止重要数据泄露。将局域网中的普通数据和重要数据进行分离,所以也可以避免内部入侵。
iptabels -t nat -A POSTROUTING -s 172.25.254.100 -j DROP
inux上查看造成IO高负载的进程
方法1:使用iotop工具
这是一个python脚本工具,使用方法如:iotop -o
方法2:使用工具dmesg
使用dmesg之前,需要先开启内核的IO监控:
echo 1 >/proc/sys/vm/block_dump或sysctl vm.block_dump=1
然后可以使用如下命令查看IO最重的前10个进程:
dmesg |awk -F: ‘{print $1}’|sort|uniq -c|sort -rn|head -n 10
方法3:使用命令“iostat -x 1“确定哪个设备IO负载高:
iostat -d -k -x 1 10
-d 表示,显示设备(磁盘)使用状态;-k某些使用block为单位的列强制使用Kilobytes为单位
-x显示扩展的信息
找“await”值最大的设备(Device),如上的结果即为sda。
然后使用mount找到sda挂载点,再使用fuser命令查看哪些进程在访问,如:
fuser -vm /data
chkconfig 和 systemd 开机启动项管理工具的区别
在centos6上的开机启动项管理工具为chkconfig
是SysV版本的,所有的开机启动服务都可以在/etc/init.d/
目录看到。
但是centos7已经不在用chkconfig
管理开机启动项,而使用的是systemd的方式
SysV启动开机进程时一次只能启动一个,而systemd则一次可以启动多个服务,这样就导致systemd的开机速度会更快。
chkconfig :
启动方式:service 服务名 start|restart|stop
服务名就是/etc/init.d/目录下的这些文件。
有些服务除了用:service crond start 之外,还可以用 /etc/init.d/crond start 启用
我们可以用 chkconfig –list 查看所有的服务及其在每个级别的开启状态。
systemd:
启动方式:systemctl start|stop|reload 服务名
它的脚本文件在:/usr/lib/systemd/system 目录下
linux 0 1号进程
0号进程即为 idle 进程或swapper进程,也就是空闲进程
1号进程即为 init 进程,后来改为systemd进程(他可以更快启动系统,更快启动多个服务,不启动不必要的服务)
整个进程创建的过程:0号进程->1号内核进程->1号用户进程(init进程)->getty进程->shell进程
shell 中的$?,$0,$*,$#,$@
$$ Shell本身的PID(ProcessID)
$! Shell最后运行的后台Process的PID
$? 最后运行的命令的结束代码(返回值)
$- 使用Set命令设定的Flag一览
$* 所有参数列表。如"$*“用「”」括起来的情况、以"$1 $2 … $n"的形式输出所有参数。
$@ 所有参数列表。如"$@“用「”」括起来的情况、以"$1" “$2” … “$n” 的形式输出所有参数。
$# 添加到Shell的参数个数
$0 Shell本身的文件名
$1~$n 后面接的参数
linux内核组成
linux系统分为用户空间(user space)和内核空间(kernel space)。其中用户空间有用户程序(user app)和函数库(C library)组成,内核空间有系统调用(system call interface),内核(kernel 狭义上的内核),设备代码组成。
2、如何从用户空间进入内核空间:
1)系统调用
2)硬件中断
3、内核的组成(子系统):
1)系统调用(SCI):为用户空间提供接口
2)进程管理(PM):进程创建删除,进程调度,进程间通信
3)内存管理(MM):地址转换(虚拟地址),内存分配
4)Arch:CPU体系代码
5)设备驱动程序(DD)
6)网络协议栈(Network Stack)
7)虚拟文件系统(VFS)
进程之间通信的8种方式
管道
消息队列
套接字
共享内存
信号量
信号
查看系统负载的命令
top
ps aux
w
uptime
sar
iostat
cat /proc/cpuinfo
linux系统中文件的特性/属性
stat zhuanzhi.sh 查看文件的信息
File: ‘zhuanzhi.sh’
Size: 354 Blocks: 8 IO Block: 4096 regular file
Device: fd00h/64768d Inode: 29077346 Links: 1
Access: (0777/-rwxrwxrwx) Uid: ( 0/ root) Gid: ( 0/ root)
Context: unconfined_u:object_r:mnt_t:s0
Access: 2020-08-29 08:42:01.689913632 +0800
Modify: 2020-08-29 08:42:00.541913689 +0800
Change: 2020-08-30 13:29:59.662291493 +0800
Birth: -
inode 号
[root@server1 mnt]# ls -lhi
total 60K
29176665 ----------. 1 root root 321 Aug 30 14:37 !
29176654 -rwxrwxrwx. 1 root root 447 Sep 12 08:38 1.sh
29176657 ----------. 1 root root 319 Aug 30 14:38 2.sh
索引节点inode包括不限于问价大小、属主(用户)、归属的用户组、文件权限、文件类型、修改时间,还包含指向文件实体的指针的功能(inode节点–block的对应关系)等,但是,inode里面唯独不包含文件名,文件名一般在上级目录的block里。Block 是用来存储实际数据用的
查看文件系统inode总量以及剩余量
df -i
查看磁盘的使用量
df -h
磁盘空间是否满了,是由两项参数决定的:第一个是inode是否满了,第二个block是否满了,任何一项满了,磁盘就不能再放东西了。
超级块
超级块是存储对应文件系统元数据的结构,存储的元数据包括包括文件系统大小,块大小,以及空闲及已使用的块的数量inode表的大小及位置等。
通常放在特定的扇区。
每个文件系统都有一个超级块结构,每个超级块都要链接到一个超级块链表。而文件系统内的每个文件在打开时都需要在内存分配一个inode结构,这些inode结构都要链接到超级块。
下图展示了超级块之间的关系以及超级块和inode之间的链接关系:
super_block1和super_block2是两个文件系统的超级块,它们被链接到super_blocks链表头。
后者使用的就是内核基础层介绍的双向链表数据结构,顺着super_blocks链表可以遍历整个操作系统的文件的inode结构。
xfs和ext文件系统
xfs
对于存储海量小文件或者超大规模文件,文件也很大,建议使用xfs。
它是一个64位文件系统,最大支持8EB减一的单个文件系统,实际部署取决于宿主操作系统的最大块限制。
从 RHEL 7 开始,XFS 成为 Red Hat Enterprise Linux 的默认文件系统
ext4
目前主流稳定的文件系统。ext4 使用 48 位的内部寻址,理论上可以在文件系统上分配高达 16 TiB 大小的文件,其中文件系统大小最高可达 1000000 TiB(1 EiB)。
ext3
ext3 文件系统使用 32 位寻址,这限制它仅支持 2 TiB 文件大小和 16 TiB 文件系统系统大小(这是假设在块大小为 4 KiB 的情况下,一些 ext3 文件系统使用更小的块大小,因此对其进一步被限制)。
ext3和ext4的区别
ext4 在将存储块写入磁盘之前对存储块的分配方式进行了大量改进,这可以显著提高读写性能。
ext3 为每一个新分配的块调用一次块分配器。当多个写入同时打开分配器时,很容易导致严重的碎片。然而,ext4 使用延迟分配,这允许它合并写入并更好地决定如何为尚未提交的写入分配块。
ext3 仅限于 32000 个子目录;ext4 允许无限数量的子目录。
ext3 提供粒度为一秒的时间戳。虽然足以满足大多数用途,但任务关键型应用程序经常需要更严格的时间控制。ext4 通过提供纳秒级的时间戳,
xfs和ext的区别
ext文件系统(支持度最广、但格式化超慢):ext系列的文件系统,在文件格式化时,采用的是规划出所有的inode、区块、元数据等数据,未来系统可以直接使用,不需要再进行动态配置,但是这个做法在早期磁盘容量还不大的时候可以使用。如今,磁盘的容量越来越大,连传统的MBR都已经被GPT取代。当使用磁盘容量在TB以上的传统ext系列文件系统在格式化的时候,会消耗相当多的时间
xfs文件系统(容量高,性能佳):由于虚拟化的应用越来越广泛,虚拟化磁盘来源的举行文件越来越常见,这些巨型文件在处理上考虑到性能问题,因此xfs比较适合高容量磁盘与巨型文件,且性能较佳的文件系统、
vfs虚拟文件系统
我们知道文件系统的种类有很多。除了Linux标准的文件系统Ext2/Ext3/Ext4外,还有很多种文件系统 。linux通过叫做VFS的中间层对这些文件系统提供了完美的支持。在大部分情况下,用户通过libc和kernel的VFS交互,不需要关心底层文件系统的具体实现。
vfs就是对各种文件系统的一个抽象,它为各种文件系统提供了一个通用的接口,把表示很多不同种类文件系统的共同信息放入内核;有了vfs,就能很容易实现不同文件系统之间的数据读写,因为它们对外接口都是一样的,都是vfs导出的通用接口。
vfs支持的文件系统的类型
磁盘文件系统 这类文件系统数目最多,最常见:ext2/ext3/ext4文件系统(关注重点)
特殊文件系统。如/proc文件系统
网络文件系统,如NFS
VFS存在的意义
向上,对应用层提供一个标准的文件操作接口;
对下,对文件系统提供一个标准的接口,以便其他操作系统的文件系统可以方便的移植到Linux上
信号、信号量
信号:是由用户、系统或者进程发送给目标进程的信息,以通知目标进程某个状态的改变或系统异常。
信号量:信号量是一个特殊的变量,它的本质是计数器,信号量里面记录了临界资源的数目,有多少数目,信号量的值就为多少,进程对其访问都是原子操作(pv操作,p:占用资源,v:释放资源)。它的作用就是,调协进程对共享资源的访问,让一个临界区同一时间只有一个进程在访问它。
信号量就是具有原子性的计数器,就相当于一把锁,在每个进程要访问临界资源时,必须要向信号量拿个锁”,它才能进去临界资源这个“房间”,并锁上门,不让其他进程进来,此时信号量执行P()操作,锁的数目减少了一个,所以计数器减1,;当它访问完成时,它出来,将锁还给信号量,执行V()操作,计数器加1;然后是下面的进程继续。这也体现了各个进程访问临时资源是互斥的。
- “原子性”:表示的是一件事情的两种状态,做了这件事和没做这件事;
- “计数器”:信号量通常描述的是临界资源的数目;同时信号量本身就是临界资源,它的目的也是保护临界资源,解决数 据不一致问题;
- “临界资源”:不同进程可以看到的那份共同的资源;
- “临界区”:多个进程访问临界资源的代码;
- “互斥”:任何时刻,只允许一个临时区访问临时资源,并且属性是原子的。
所以它们两的区别也就显而易见了,信号是通知进程产生了某个事件,信号量是用来同步进程的(用来调协进程对共享资源的访问的)
信号 1-31:
nginx升级时使用的信号
服务
常见的端口:
端口 | 服务 |
---|---|
7 | echo |
21 | ftp |
22 | ssh |
23 | telnet |
53 | dns |
80 | http |
443 | https |
123 | ntp网络时间协议 |
6379 | redis |
1521 | oracle |
3306 | mysql |
apache 和 nginx的区别
两者最核心的区别在于:
Apache是同步多进程模型(同步阻塞),一个连接对应一个进程,而Nginx是异步的(异步非阻塞),多个连接(万级别)可以对应一个进程。
Nginx相对于Apache的优势:
1…轻量级,占用更少的内存及资源
2.抗高并发,处理请求是异步非阻塞的,多个连接对应一个进程,负载能力比apache高很多,在高并发下nginx能保持低资源低消耗高性能
3.作为负载均衡服务器,支持7层负载均衡
4.本身就是一个反向代理服务器,而且可以作为非常优秀的邮件代理服务器
5.nginx对静态图片的处理更优秀,但是动态图片必须通过php fastcgi的方式进行解析
6.一个线程处理多个请求, 《事件驱动》
Apache相对于Nginx的优势:
1.apache的rewrite比nginx强大,在rewrite频繁的情况下,用apache
2.apache发展时间长,支持的模块比较多
3.apache更为成熟,少bug ,nginx的bug相对较多
4.apache超稳定,ngin一个进程挂掉时,会影响到多个用户的使用,稳定性差
5.为每个情趣创建新线程《过程驱动》
适用场景:
一般来说,需要性能的web服务,用Nginx;如果不需要性能只求稳定,更考虑Apache;
所以更为通用的方案是,前端Nginx抗并发,后端Apache集群,配合起来会更好。
同步阻塞/同步非阻塞,异步阻塞/异步非阻塞
普通水壶、:必须旁边等着水开
响水壶:谁开了会响,提示效果
老王:相当于 进/线程
1 老张把水壶放到火上,等水开。(同步阻塞)
2 老张把水壶放到火上,去客厅看电视,时不时去厨房看看水开没有。(同步非阻塞)
3 老张把响水壶放到火上,等水开。(异步阻塞),无任何效果。
4 老张把响水壶放到火上,去客厅看电视,水壶响之前不再去看它了,响了再去拿壶。(异步非阻塞)
同步就是老王必须盯着水壶,不同步是烧水时老王就去看电视了
阻塞是老王一直盯着水壶,非阻塞是老王可以临时去干别的事。
nginx 惊群
多线程/多进程(Linux下线程进程也没多大区别)等待同一个socket事件,当这个事件发生时,这些线程/进程被内核重新调度唤醒,就是惊群。许多进程被,同时去响应这一个事件,当然只有一个进程能处理事件成功,其他的进程在处理该事件失败后重新休眠。这种性能浪费现象就是惊群;如何解惊群问题;回答(锁,红黑树,定时器)
四层负载均衡和七层负载均衡的区别
四层负载均衡
- 四层的负载均衡就是基于IP+端口的负载均衡:在
三层负载均衡的基础
上,通过发布三层的IP地址
(VIP),然后加四层的端口号
,来决定哪些流量需要做负载均衡,对需要处理的流量进行NAT处理,转发至后台服务器,并记录下这个TCP或者UDP的流量是由哪台服务器处理的,后续这个连接的所有流量都同样转发到同一台服务器处理。 - 所谓四层负载均衡,也就是主要通过报文中的目标地址和端口,再加上负载均衡设备设置的服务器选择方式,决定最终选择的内部服务器。
七层负载均衡
- 七层负载均衡(根据虚拟的url或是IP,主机名接收请求,再转向相应的处理服务器):在
四层负载均衡的基础
上(没有四层是绝对不可能有七层的),还可根据七层的URL、浏览器类别、语言来决定是否要进行负载均衡。 - 所谓七层负载均衡,也称为“内容交换”,也就是主要通过报文中的真正有意义的应用层内容,再加上负载均衡设备设置的服务器选择方式,决定最终选择的内部服务器。
二层负载均衡
- 负载均衡服务器对外依然提供一个VIP(虚IP),集群中不同的机器采用相同IP地址,但是机器的MAC地址不一样。当负载均衡服务器接受到请求之后,通过改写报文的目标MAC地址的方式将请求转发到目标机器实现负载均衡。
三层负载均衡
- 和二层负载均衡类似,负载均衡服务器对外依然提供一个VIP(虚IP),但是集群中不同的机器采用不同的IP地址。当负载均衡服务器接受到请求之后,根据不同的负载均衡算法,通过IP将请求转发至不同的真实服务器。
七层更智能,更安全,更复杂,四层效率更好一点
七层主要应用于http,四层tcp
oracle数据库概念
ftp的两种工作模式
总的来说,主动模式的FTP是指服务器主动连接客户端的数据端口,被动模式的FTP是指服务器被动地等待客户端连接自己的数据端口。
active ftp 主动模式:
FTP客户端随机开启一个大于1024的端口N向服务器的21号端口发起连接,然后开放N+1号端口进行监听,并向服务器发出PORT N+1命令。服务器接收到命令后,会用其本地的FTP数据端口(通常是20)来连接客户端指定的端口N+1,进行数据传输。
被动模式
在被动模式下,FTP库户端随机开启一个大于1024的端口N向服务器的21号端口发起连接,同时会开启N+1号端口。然后向服务器发送PASV命令,通知服务器自己处于被动模式。服务器收到命令后,会开放一个大于1024的端口P进行监听,然后用PORT P命令通知客户端,自己的数据端口是P。客户端收到命令后,会通过N+1号端口连接服务器的端口P,然后在两个端口之间进行数据传输。
cdn 内容分发网络
CDN:Content Delivery Network
肯德基的总部在美国,但是全世界走很多分店,这些分店就是cdn。分店里面的单品就是内容
CDN专注于「内容」,也就是CDN的C所代表的Content,专注于静态资源的分发和访问,比如一张图片,一个文本文件,一个视频,一个CSS,一个JS等等,任何以文件形式存储的,为了提高在互联网上的访问速度和质量,都可以将这个资源部署在CDN这个网络上。
CDN动作是「分发」,也就是如何让刚才提到的那些「内容」快速的部署在这个网络中,从而快速为用户服务,其实还有一层更重要的含义是用户的快速访问与就近接入,分发的目的是为了用户更好的体验。
CDN落定于「网络」,是部署于全国或者全世界的一大堆服务器,这些服务器基于当前互联网的基础架构在其上层再构成一个网络,这个网络专为资源分发而生。
作用
- 应用服务器和资源服务器应该解耦
- 跨运营商加速:我们自己的网站常常只属于一个运营商(比如:电信),而加速节点遍布每家运营商,于是和网站不同运营商(比如:联通)的用户访问起来就不会那么慢了。
- 缓存加速:很多的静态资源以及一部分页面更新都是比较慢的(比如首页),这个时候CDN就会根据浏览器的max-age和last-modified值以及管理员的预设值来进行缓存,于是很多流量CDN节点就不会每次都来向网站请求,CDN节点可以直接自作主张地将命中的缓存内容返回。
- 恶意流量过滤:这是CDN非常重要的一个作用,也是很多网站会用CDN的原因,因为CDN能为我们抵挡攻击大流量攻击、普通的攻击(比如注入等),只有正常流量才会转发给网站。
CDN流量通俗来讲就是使用CDN加速时,网络加速会产生一个数据使用量,到达某一个时段,统计出这个时段使用的量,也就是CDN流量,和网站流量的使用很像。
CDN流量计费方式一般分为2种:流量计费和带宽计费(划算)
1、流量计费是简单的累积当月流量 * 流量单价 + 请求数 * 请求单价。就是用户访问你网站所消耗的流量
2、而带宽计费一般为平均计费、九五计费和第四峰值计费,并且维度为5分钟。带宽是根据流量换算过来的。这种的话不计算流量,只计算带宽。
缺点:
- 只可以对静态内容加速
- 内容更新的时候需要分发同步到其他所有的节点,可能会存在不实时同步的情况。解决方法是在网络内容发生变化时将新的网络内容从服务器端直接传送到缓存器。
- 代价高昂
监控都可以监控哪些内容
服务器:
cpu(利用率)
内存(已使用,剩余)
swap空间
磁盘空间大小
磁盘I/O
系统中的进程数量,线程数量
网络:
网络流量,上下行速率
连接的ip,连接的数量
监控vip或端口是否打开
web应用:
服务并发量
服务的响应时间
数据库:
数据库的操作频率
并发连接量
系统
session 和 cookie 的区别
session 和cookie 都是会话技术,session 工作在服务端,cookie 工作在客户端,
Cookie实际上是一小段的文本信息。客户端请求服务器,服务器向客户端浏览器颁发一个Cookie
客户端浏览器会把Cookie保存起来。当浏览器再请求该网站时,浏览器把请求的网址连同该Cookie一同提交给服务器。但是当cookie过多时会浪费网络资源。
session
只要求客户端回传一个 ID
即可,这个 ID 是客户端第一次
访问服务器的时候生成的, 而且每个客户端是唯一
的。这个 ID 通常是 NANE 为JSESIONID 的一个 Cookie。
场景:
cookie: 分给顾客一张卡片,每消费一次记录一次,由客户保存;
session : 发给顾客一张卡片,上面有卡号,顾客每消费一次,由店员在操作机上记录一次,顾客只需记住ID。
cookie 不安全,通过本地文件可以进行攻击。
fastcgi 和 cgi 的区别
cgi: 通用网关接口,处理完请求时随机结束进程,然后在开启下一个进程处理下一个请求。
fastcgi: 进程一直存在,不需要 fork 新进程来处理请求,并可以启动多个cgi解释器,来一直处理请求,处理完这一个,就等待下一个请求。
进程,线程,协程的区别
https://blog.csdn.net/thermal_life/article/details/106112894
协程其实可以理解为是 “用户态” 的多线程。在多线程的模型中,操作系统会根据某种调度算法不断地切换当前正在运行的线程,由于每个线程都有自己的栈,因此在切换线程的过程中需要上下文的切换,这样会导致大量的开销,如果系统中多大量的线程,那么系统的资源就会被上下文的切换大量的消耗,导致性能的下降。协程就是用来解决这个问题的(当然还有其他优点),协程运行在同一个线程上,没**有 系统级别上下文的切换 **。协程 拥有自己的寄存器上下文和栈 。协程调度切换时,将寄存器上下文和栈保存到其他地方,在切回来的时候,恢复先前保存的寄存器上下文和栈。因此:协程能保留上一次调用时的状态。
协程 不需要多线程的锁机制 。由于 只有一个线程 ,也不存在同时写变量的冲突,在协程中控制共享资源不需要加锁,只需要判断数据的状态,所以执行效率远高于线程 ,
对于多核CPU可以使用 多进程+协程 来尽可能 高效率地利用CPU。
线程的上下文切换
CPU通过时间片分配算法来循环执行任务(线程),因为时间片非常短,所以CPU通过不停地切换线程执行。
时间片是CPU分配给各个任务(线程)的时间!
线程切换,同一进程中的两个线程之间的切换
进程切换,两个进程之间的切换
模式切换,在给定线程中,用户模式和内核模式的切换
地址空间切换,将虚拟内存切换到物理内存
CPU切换前把当前任务的状态保存下来,以便下次切换回这个任务时可以再次加载这个任务的状态,然后加载下一任务的状态并执行。任务的状态保存及再加载, 这段过程就叫做上下文切换。
过程:
挂起当前任务(线程/进程),将这个任务在 CPU 中的状态(上下文)存储于内存中的某处
恢复一个任务(线程/进程),在内存中检索下一个任务的上下文并将其在 CPU 的寄存器中恢复
跳转到程序计数器所指向的位置(即跳转到任务被中断时的代码行),以恢复该进程在程序中。
用户态和内核态的切换
当在系统中执行一个程序时,大部分时间是运行在用户态下的,在其需要操作系统帮助完成一些用户态自己没有特权和能力完成的操作时就会切换到内核态。
用户态切换到内核态的3种方式
(1)系统调用
这是用户态进程主动要求切换到内核态的一种方式。用户态进程通过系统调用申请使用操作系统提供的服务程序完成工作。
(2)异常
用户态下的程序时,发生了一些没有预知的异常,这时会切换到处理此异常的内核相关进程中
(3)外围设备的中断
长链接和短连接的区别
短连接:连接->传输数据->关闭连接
指SOCKET连接后,发送接收完数据后马上断开连接。
长连接:连接->传输数据->保持连接 -> 传输数据-> …->直到一方关闭连接,多是客户端关闭连接。
长连接指建立SOCKET连接后不管是否使用都保持连接,但安全性较差。
数据库 的连接用 长连接 ,WEB网站 的http服务一般都用 短链接,因为长连接会 耗费服务端一定 资源,而像WEB网站成千上万的连接用短连接会更省一些资源,网络游戏 应用都是长连接。
cache(读)和buffer(读写)的区别
-
Cache:缓存区,是高速缓存,是位于CPU和主内存之间的容量较小但速度很快的存储器,因为CPU的速度远远高于主内存的速度,CPU从内存中读取数据需等待很长的时间,而 Cache保存着CPU刚用过的数据或循环使用的部分数据,这时从Cache中读取数据会更快,减少了CPU等待的时间,提高了系统的性能。启提高访问速度的作用。
Cache并不是缓存文件的,而是缓存块的(块是I/O读写最小的单元);Cache一般会用在I/O请求上,如果多个进程要访问某个文件,可以把此文件读入Cache中,这样下一个进程获取CPU控制权并访问此文件直接从Cache读取,提高系统性能。
-
Buffer:缓冲区,主要目的是进行流量整形,把突发的大数量较小规模的 I/O 整理成平稳的小数量较大规模的 I/O,以减少响应的次数
Buffer:一般是用在写入磁盘的,例如:某个进程要求多个字段被读入,当所有要求的字段被读入之前已经读入的字段会先放到buffer中,等到全部字段读入在写入磁盘,来进行缓冲。
独立冗余磁盘阵列RAID
RAID0技术把多块(至少两块)物理硬盘设备通过软件或硬件的方式串联在一起,组成一个大的卷组,并将数据依次写入到各个物理硬盘中。
备的读写性能会提升数倍,但是若任意一块硬盘发生故障将导致整个系统的数据都受到破坏。
如果生产环境对硬盘设备的读写速度没有要求,而是希望增加数据的安全性时,就需要用到RAID1技术了。
RAID1技术示意图如下图,它是把两块以上的硬盘设备进行绑定,在写入数据时,是将数据同时写入到多块硬盘设备上(可以将其视为数据的镜像或备份)。当其中某一块硬盘发生故障后,一般会立即自动以热交换的方式来恢复数据的正常使用。导致利用率下降只有50%
RAID5技术是把硬盘设备的数据奇偶校验信息保存到其他硬盘设备中。
就是RAID5技术实际上没有备份磁盘中的真实数据信息,而是当硬盘设备出现问题后通过奇偶校验信息来尝试重建损坏的数据。
兼顾了硬盘设备的读写速度、数据安全性与存储成本问题
RAID10即RAID0+RAID1的一个组合体。如下图所示,RAID10技术需要至少4块硬盘来组建,
先分别两两制作成RAID1磁盘阵列,以保证数据的安全性;然后再对两个RAID1次哦按阵列实施RAID0技术
灰度测试,蓝绿测试,A/B测试
蓝绿测试
线上有两套集群环境,一套称为蓝色集群BLUE;一套称为绿色集群GREEN。通过将流量引入两个集群,完成系统升级切换。
步骤一:部署绿色集群,这个时候是初始状态,蓝色集群承担全部责任,接收全部流量,等待被替换。绿色集群刚刚部署,还没有投入使用,流量为0,等待验证和上线。
步骤二:蓝色集群流量不变,向绿色集群引入流量。这个过程可以分成几个阶段完成。第一个阶段,引入少量非实时流量,仅用于数据测试;第二个阶段,引入全部实时流量,用于做系统验证。
步骤三:切断向蓝色集群引入流量,将全部流量引入绿色集群。这个时候,绿色集群已经承担全部责任,接收全部流量。这个过程也可以分阶段操作。一,平衡蓝色和绿色集群流量,也就是蓝色和绿色集群一同承担职责;第二个阶段,切断蓝色集群流量,流量全部写入绿色集群。是否采用分阶段操作,完全看升级的功能是否是破坏性的,是否可兼容。
步骤四:监控系统运行。
灰度发布
它能够缓慢的将修改推广到一小部分用户,验证没有问题后,再推广到全部用户,以降低生产环境引入新功能带来的风险。
步骤一:将流量从待部署节点移出,更新该节点服务到待发布状态,将该节点称为金丝雀节点;
步骤二:根据不同策略,将流量引入金丝雀节点。策略可以根据情况指定,比如随机样本策略(随机)、狗粮策略(员工)、分区策略(不同区域)、用户特征策略
步骤三:金丝雀节点验证通过后,选取更多的节点称为金丝雀节点。
AB测试
AB测试和上面两种发布方式不是一个范围的概念,它是为了进行效果验证的手段,
将一部分流量引入A版本,另外一部分流量引入B版本,也可能出现CDEF版本。然后相关人员通过分析不同版本的实际效果,选出最优解。
系统中的进程
R(TASK_RUNNING) 可执行状态(RUNNING,READY)
S(TASK_INTERRUPTIBLE) 可唤醒睡眠状态
D (TASK_UNINTERRUPTIBLE) 不可唤醒睡眠状态
T(TASK_STOPPED) 暂停状态
z( EXIT_ZOMBIE) 僵死态
子进程结束后父进程没有收到子进程的返回码,就会出现僵尸进程。
避免僵尸进程:
让僵尸进程的父进程结束kill -9,变为孤儿僵尸进程,就会被init进程领养,最终被回收。
二叉树的三种遍历
对于二叉树,有深度遍历和广度遍历,深度遍历有前序、中序以及后序三种遍历方法,广度遍历即我们平常所说的层次遍历。
前序遍历
a、访问根节点;b、前序遍历左子树;c、前序遍历右子树。
12457836
中序遍历
a、中序遍历左子树;b、访问根节点;c、中序遍历右子树。
42758136
后序遍历
a、后序遍历左子树;b、后续遍历右子树;c、访问根节点。
47852361
反向代理和正向代理
1、正向代理:
正向代理,代理的是客户端。正向代理就是 代理服务器 替代 客户端 去访问 目标服务器
如浏览器中设置代理,代替访问Internet资源就属于正向代理
2、反向代理
反向代理,代理的是服务端。就是 代理服务器 替代 服务器 去向 客户端 返回资源
如nginx应用于服务端,做WEB服务的负载均衡,此时nginx就是反向代理。
堆栈,队列的区别
队列是先进先出,有出口和入口,先进去可以先出来。
栈先进后出,就像一个箱子,后放上去的,可以先出来
{堆(Heap)是应用程序在运行的时候请求操作系统分配给自己内存。而栈只是指一种使用堆的方法(即先进后出)。对其访问和对一般内存的访问没有区别。
栈是先进后出的,但是于堆而言却没有这个特性,两者都是存放临时数据的地方。 对于堆,我们可以随心所欲的进行增加变量和删除变量,不要遵循什么次序,只要你喜欢。
中间件
web中间件:tomcat,nginx,htt:
消息中间件:rocketMQ,rabbitMQ,kafka
其他:zookeeper,hdfs,fastDFS,redis分布式缓存,分布式消息kafka
数据库中间件: MyCAT,Cobar(阿里)
消息队列
“消息队列”是在消息的传输过程中保存消息的容器。
消息队列(Message Queue)是一种应用间的通信方式,消息发送后可以立即返回,有消息系统来确保信息的可靠专递,消息发布者只管把消息发布到MQ中而不管谁来取,消息使用者只管从MQ中取消息而不管谁发布的,这样发布者和使用者都不用知道对方的存在。
消息队列是一种应用间的异步协作机制,应用于业务解耦的情况,其他常见场景包括最终一致性、广播、错峰流控等等。
keepalived和哨兵的区别
- keepalived的配置相对简单,可配置的比较少,哨兵比较繁琐
- 哨兵用于redis的高可用时导致redis不可扩容
- 哨兵本身没有高可用。
常见linux发行版本
Linux 的发行版本可以大体分为两类:
商业公司维护的发行版本,以著名的 Red Hat 为代表;
社区组织维护的发行版本,以 Debian 为代表。
red Hat 公司的产品主要包括 RHEL(Red Hat Enterprise Linux,收费版本)和 CentOS(RHEL 的社区克隆版本,免费版本)、Fedora Core(由 Red Hat 桌面版发展而来,免费版本)。
Ubuntu 基于知名的 Debian Linux 发展而来,具有优秀的桌面环境,容易上手,对硬件的支持非常全面,是目前最适合做桌面系统的 Linux 发行版本,
Linux 的发行版本众多,在此不逐一介绍,下面给选择 Linux 发行版本犯愁的朋友一点建议:
如果你需要的是一个服务器系统,而且已经厌烦了各种 Linux 的配置,只是想要一个比较稳定的服务器系统,那么建议你选择 CentOS 或 RHEL。
如果你只是需要一个桌面系统,而且既不想使用盗版,又不想花大价钱购买商业软件,不想自己定制,也不想在系统上浪费太多时间,则可以选择 Ubuntu。
如果你想深入摸索一下 Linux 各个方面的知识,而且还想非常灵活地定制自己的 Linux 系统,那就选择 Gentoo 吧,尽情享受 Gentoo 带来的自由快感。
如果你对系统稳定性要求很高,则可以考虑 FreeBSD。
如果你需要使用数据库高级服务和电子邮件网络应用,则可以选择 SuSE。
数据库
关系型和非关系型数据库
关系型:oracle,mysql,DB2,SQLserver,有一定的数据结构
非关系型:redis(分布式键值对),mongoDB(面向文档),memcached(分布式缓存)
对比:非关系型支持更高的并发,读写速度更快,易于扩展可伸缩。事务支持较弱,通用性差,复杂场景不好用。
关系型具有acid性质,容易理解,方便维护,降低了数据冗余。高并发下性能不足,有I/O瓶颈,而且有固定表结构,不易于拓展。
acid性质
-
原子性
事物操作是一个不可分割的单位,要么同成功,要么同失败。 -
一致性
事务操作之后,前后是一致的。例如a账户给b账户转账100,前后a要少了100,b要多了100,总和还是100。 -
隔离性
多个事务并发访问时,事务之间是隔离的,一个事务不应该影响其它事务运行效果。
并发环境中,当不同的事务同时操纵相同的数据时,每个事务都有各自的完整数据空间。
企业开发中,事务最复杂问题都是由事务隔离性引起的。
事务直接所可能造成的问题:(不是数据库的隔离级别)-
脏读:总结:一个事务读取另一个事务未提交的数据时,这个数据可能会回滚。
-
不可重复读:不可重复读意味着,在数据库访问中,一个事务范围内两个相同的查询却返回了不同数据。这是由于查询时系统中其他事务修改(update、insert或delete(幻读))的提交而引起的。
-
丢失更新
同时修改一条记录,后者覆盖前者数据,前者丢失更新。
-
-
持久性
事务操作后的结果永久反应在数据库中了。
锁
锁类型:
共享锁:由读表操作加上的锁,加锁后其他用户只能获取该表或行的共享锁,不能获取排它锁,也就是说只能读不能写
排它锁:由写表操作加上的锁,加锁后其他用户不能获取该表或行的任何锁,典型是mysql事务中的
锁的范围:
行锁: 对某行记录加上锁
表锁: 对整个表加上锁
这样组合起来就有,行级共享锁,表级共享锁,行级排他锁,表级排他锁
隔离级别
- 读未提交(read uncommit)
一级封锁协议(读取数据的时候不加锁,更新的时候整个加X锁)
b事物执行到一半,a事物不检测锁直接读取,结果b事物回滚了,导致a事物读出了一个错的结果,这就是脏读。
- 读已提交(read committed)
二级封锁协议(读取数据的时候加S锁,更新的时候加X锁)
a事物每次读取的时候都会尝试获取s锁,如果b事物在更新,则a阻塞等待b事物释放。
解决了脏读的问题。
因为a读取完毕以后直接释放,如果a事物有两次读取操作,而在这期间b更新了数据,
会导致两次结果不一样。这就是不可重复读
- 可重复读(repeatable read)
三级封锁协议(对读取数据的整个事务加S锁,更新的时候整个加X锁)
因为a读取操作整个加了s锁,所以在此期间b事物不能获得x锁。这样就解决了不可重复读问题。
幻读a在读表的时候,b往表里删除行,导致a统计的结果和表里现在的不一致,好像发生了幻觉。(幻读来源于表行的增加或删除,解决幻读只能对表加锁)
- 序列化(sirializable)
锁全表(事物不并发执行)
解决了幻读现象。
数据库的四种范式
第一范式(1NF):数据库表中的字段都是单一属性的,不可再分。
第二范式(2NF):数据库表中不存在非关键字段对任一候选关键字段的部分函数依赖:
第三范式(3NF):在第二范式的基础上,表中不存在非关键字段对任一候选关键字段的传递函数依赖则符合第三范式。(A>B>C)。
第四范式(4NF):在第三范式的基础上,表中如果不存在任何字段对任一候选关键字段的传递函数依赖则符BCNF范式。
(仓库ID, 存储物品ID) →(管理员ID, 数量)
(管理员ID, 存储物品ID) → (仓库ID, 数量)
所以,(仓库ID, 存储物品ID)和(管理员ID, 存储物品ID)都是StorehouseManage的候选关键字,表中的唯一非关键字段为数量,它是符合第三范式的。但是,由于存在如下决定关系:
(仓库ID) → (管理员ID)
(管理员ID) → (仓库ID)
即存在关键字段决定关键字段的情况,所以其不符合BCNF范式。
Myisam和Innodb的区别
-
InnoDB支持事务,MyISAM不支持,对于InnoDB每一条SQL语言都默认封装成事务,自动提交,这样会影响速度,所以最好把多条SQL语言放在begin和commit之间,组成一个事务;
-
InnoDB支持外键,而MyISAM不支持。对一个包含外键的InnoDB表转为MYISAM会失败;
-
InnoDB是聚集索引,使用B+Tree作为索引结构,数据文件是和(主键)索引绑在一起的(表数据文件本身就是按B+Tree组织的一个索引结构),必须要有主键,通过主键索引效率很高。但是辅助索引需要两次查询,先查询到主键,然后再通过主键查询到数据。因此,主键不应该过大,因为主键太大,其他索引也都会很大。
MyISAM是非聚集索引,也是使用B+Tree作为索引结构,索引和数据文件是分离的,索引保存的是数据文件的指针。主键索引和辅助索引是独立的。 -
innoDB不保存表的具体行数,执行select count(*) from table时需要全表扫描。而MyISAM用一个变量保存了整个表的行数,执行上述语句时只需要读出该变量即可,速度很快(注意不能加有任何WHERE条件);
-
Innodb不支持全文索引,而MyISAM支持全文索引,在涉及全文索引领域的查询效率上MyISAM速度更快高;PS:5.7以后的InnoDB支持全文索引了
-
MyISAM表格可以被压缩后进行查询操作
-
InnoDB支持表、行(默认)级锁,而MyISAM支持表级锁
-
InnoDB表必须有唯一索引(如主键)(用户没有指定的话会自己找/生产一个隐藏列Row_id来充当默认主键),而Myisam可以没有
-
Innodb存储文件有frm、ibd,而Myisam是frm、MYD、MYI
Innodb:frm是表定义文件,ibd是数据文件 Myisam:frm是表定义文件,myd是数据文件,myi是索引文件
为什么不把数据库部署在docker中
- 数据安全问题
容器的生命周期很脆弱,很容易被删除,停止。或在使用卷挂载的时候容器出现问题,就会丢失数据。 - 性能问题
数据库的性能瓶颈就出在 I/O 上,当运行多个数据库容器的时候,I/O就会累加,降低sql读写性能。 - 网络问题
- 状态
容器中的水平伸缩只适合于无状态的服务,而数据库运行在容器中是有状态的 - 资源隔离
docker使用cgroup进行资源的隔离,限制资源最大使用量,还有很多的无法隔离,比如时间,桥接网络。是不如kvm 的 - 云平台的不适用行
云平台提供了不用为硬件操心的便利性,如果数据库运行在容器上,便利性就不存在了。
双主架构优缺点
双主架构实现方案
1、主备模式,两台MySQL互为主从,其中一台作为主节点对外提供服务,另外一台作为备机节点(standby),当提供服务的主节点发生故障后,将服务请求快速切换到备用节点,原主节点故障恢复后转换为备用节点(standby)。
2、主主模式,两台MySQL互为主从,且两台MySQL均作为主节点对外提供服务,当其中一台MySQL发生故障后,将指向该故障节点的请求快速切换到另外一台MySQL,原来指向非故障节点的请求不受影响。
双主架构优点
1、主主模式能将读写请求分摊到两个主节点,有效提升服务器使用率。
2、主节点发生故障后,能快速进行主从切换。
3、当故障节点恢复后,故障节点能通过复制进行数据恢复(应用其他节点数据)和数据同步(将未同步数据发生给其他节点)。
双主架构缺点
1、当主节点上MySQL实例发生故障后,可能会存在部分数据(Binlog)未同步到另外的主节点,导致数据丢失(直到故障节点恢复)。
2、主主模式下,很容易因数据访问控制不当导致数据冲突。
3、为提高系统高可用性,双主架构会被扩展成双主多从结构,同样存在主节点发生故障后多个从库选主和恢复复制的问题。
4、另一台主节点可能会一直处于空闲状态(可以用它当从库,负责部分查询);
5、主库后面提供服务的从库要等masterB先同步完了数据后才能去masterB上去同步数据,这样可能会造成一定程度的同步延时;
mysql的三种查询方式
- 内连接查询 inner join
SELECT boy.hid,boy.bname,girl.gname FROM boy INNER JOIN girl ON girl.hid = boy.hid;
在boy表和girl 表中查出两表 hid 字段一致的姓名(gname,bname),boy表和girl 表如下
查询结果如下:
- 左连接查询 left join
left join 是left outer join的简写,它的全称是左外连接,是外连接中的一种。 左(外)连接,左表(a_table)的记录将会全部表示出来
,而右表(b_table)只会显示符合搜索条件的记录
。右表记录不足的地方均为NULL
。
SELECT boy.hid,boy.bname,girl.gname FROM boy RIGHT JOIN girl ON girl.hid = boy.hid;
- 右连接 right join
与左连接相反,左表(a_table)只会显示符合搜索条件的记录,而右表(b_table)的记录将会全部表示出来
SELECT boy.hid,boy.bname,girl.gname FROM boy RIGHT JOIN girl ON girl.hid = boy.hid;
数据库的约束
1.主键 primary:物理上的存储顺序
2.非空 not null:此字段值不能为空
3.唯一 uniqe:此字段的值不能重复
4.默认default:字段不设置值的时候采用默认值
5.外键foreign key:表的外键是别的表的主键,
数据库设计
1.遵从前三个范式(有问题就拆分成多个表)
2.E-R模型 / 实体关系模型
一对一的时候,在任一表添加字段都可以
一对多的时候需要在多的表添加字段;(一个父母多个儿子时,需要在儿子表进行添加父母字段)
多对多的时候需要新建一张表。(学生和课堂)
一些操作
- 创建一个新表
create table goods_cate (
id int unsigned primary key auto_increment,
name varchar(40) not null);
- 把表的一个字段放入另外一张表
insert into goods_cate (name) select cate_name from goods group by cate_name
- 1和2同时进行
create table goods_cate (
id int unsigned primary key auto_increment,
name varchar(40) not null) select cate_name as name from goods group by cate_name
- 把表的一个字段值更新为另一个表的字段的值
update goods as g inner join goods_cate as c om g.cate_name = c.name set name = c.id
- 更改字段名和属性:
//change可以进行重命名,modify不重命名
alter table goods change cate_name cate_id int unsigned nut null
6.添加外键:
//外键用来确定cate_id和id进行对应,避免插入了不正确的值
吧goods表的cate_id添加为外键,关联goods_cate 表的主键id
alter table goods add foreign key (cate_id) references goods_cate(id)
7.取消外键
实际开发很少用外键,因为会限制更新的效率。
show create table goods //查看外键名字
alter table goods drop foreign key 外键名