广播和组播
数据包在以太网物理介质上传播之前必须封装头部和尾部信息。封装后的数据包称为称为数据帧
,数据帧中封装的信息决定了数据如何传输。
![](https://i-blog.csdnimg.cn/blog_migrate/76ad479dd30a0de2f1da3eca2a3a634b.png)
MAC = OUI(24bit) + 供应厂商提供(24bit)
![](https://i-blog.csdnimg.cn/blog_migrate/27c31a4bc19315d480d7fb12ed912a28.png)
![](https://i-blog.csdnimg.cn/blog_migrate/75c1974ae10812a76fc5dfba315bd67f.png)
单播详细:
在局域网中,所有主机都能收到源主机发送的单播帧,但是其他主机发现目的地址不本地MAC地址不一致后会丢弃收到的帧,只有真正的目的主机才会接收并处理收到的帧。
![](https://i-blog.csdnimg.cn/blog_migrate/9782511965148421956abe8815b8b06e.png)
广播详细:(只能在局域网中传输,
路由器不会转发广播
)
广播帧的目的MAC地址为十六进制的FF:FF:FF:FF:FF:FF,所有收到该广播帧的主机都要接收并处理这个帧。
![](https://i-blog.csdnimg.cn/blog_migrate/4558d5cdd142cf54a6d063c1a78ec1a6.png)
当ip为广播时,那么
目的MAC地址
就会被自动设为
FF:FF:FF:FF:FF:FF(
广播mac
)。
![](https://i-blog.csdnimg.cn/blog_migrate/50ee4ca2ccffcd7881ec846edc62de42.png)
函数实现:
发送方:
缺省创建的套接字不允许广播数据包,需要设置属性
int socket(int domain, int type, int protocol);
- domain : 协议族 AF_INET
- type : 套接字的类型
SOCK_STREAM、SOCK_DGRAM、SOCK_RAW
流式套接字、数据报套接字、原始套接字
- protocol : 协议
(一般设置为0表示选择默认协议,只有原始套接字不能写0而需要根据具体协议选择)
setsockopt可以设置套接字属性,
超时检测等等都是用它
int broadcast = 1;
(1)if (setsockopt(sockfd, SOL_SOCKET,
SO_BROADCAST, &broadcast, sizeof(broadcast)) < 0 )
(2)接收方地址指定为广播地址
targetaddr.sin_addr.s_addr = htonl(
INADDR_BROADCAST); /*
255.255.255.255 */
targetaddr.sin_addr.s_addr = inet_addr(“192.168.1.255”); /*该网段的广播地址*
接收方:
绑定IP地址(
广播IP或0.0.0.0)和端口绑定的端口(必须和发送方指定的端口相同)
192.168.1.255 / 255.255.255.255
组播详细:
![](https://i-blog.csdnimg.cn/blog_migrate/4ad891032f43935759df4ca926dd610a.png)
![](https://i-blog.csdnimg.cn/blog_migrate/ce4c1805f622d34bbadf5a7b2b2c9410.png)
前面
0x01005e0固定了,开头有个01,也就是第8为位是1,所以
组播MAC地址和单播MAC地址是通过第一字节中的第8个比特区分的。 组播MAC地址的第8个比特为1,而单播MAC地址的第8个比特为0。
![](https://i-blog.csdnimg.cn/blog_migrate/757fcc7023e795b81ddc95fed3fa6c47.png)
发播的主机:
目的IP为D类IP,则会生成对应的mac地址,
接收主机:
加入目的IP(有对应函数),也会生成对应mac地址(和上面一样),接收主机会检测两个mac
![](https://i-blog.csdnimg.cn/blog_migrate/6a3c2cd8275dcedff36075ca44176bdb.png)
IP协议会识别出来的,不符合就丢弃
![](https://i-blog.csdnimg.cn/blog_migrate/ad412127f77040f535bff99aade01dfc.png)
找套接字选项手册
man 7 tcp
man 7 ip
![](https://i-blog.csdnimg.cn/blog_migrate/f74bb26e3eccef5102b058d90f51efff.png)
![](https://i-blog.csdnimg.cn/blog_migrate/756283e4b1a9e3702d3860e37af2f489.png)
![](https://i-blog.csdnimg.cn/blog_migrate/00a9e9e45f4133361981722643555d15.png)
unix域套接字
![](https://i-blog.csdnimg.cn/blog_migrate/ccee483eca5785cefe9dc5cbe574fe2c.png)
![](https://i-blog.csdnimg.cn/blog_migrate/e66657b665ead15f3b34d0cd2356d027.png)
服务器端流程
![](https://i-blog.csdnimg.cn/blog_migrate/2b2422b204b86ce183d937814e370234.png)
客户端流程
![](https://i-blog.csdnimg.cn/blog_migrate/8f451e84daa42599d07887c2c97935ef.png)
地址信息结构体
![](https://i-blog.csdnimg.cn/blog_migrate/9aba971c8c8984d7cbda2e389df63dd3.png)
代码:
![](https://i-blog.csdnimg.cn/blog_migrate/a77326785bcc942615173ada4125effa.png)
sun_path是字符数组,只能传值
![](https://i-blog.csdnimg.cn/blog_migrate/c84c7ce9004cf5f75d348b47bd183053.png)
注意:
![](https://i-blog.csdnimg.cn/blog_migrate/221bc11e36fd970716f7a07ede1e0c4b.png)
报式套接字:(和流式差不多)
注意:
![](https://i-blog.csdnimg.cn/blog_migrate/550e5d795d5408a018d2999057887061.png)
udp时
bind
服务器与客户端两边都需要。
套接字是类似管道文件的(流/报),流式的话,数据传输完全按次序读写(不要忘了ACK),所以
单一文件
也不会有问题
但是报式的话,灭有次序的。客户端
发包给服务端的文件
,服务端
发包给客户端的文件。
![](https://i-blog.csdnimg.cn/blog_migrate/06b3933ebad878e06e9e8a78f78aa1b4.png)
--------------------------------------------------------绝望的分割线-----------------------------------------------------------
数据库了!!!!尼玛,好快
数据库(Database)
数据库是在数据库
管理系统管理和控制之下,存放在存储介质上的
数据集合。
按照一定数据结构存储
用一个管理系统来管理数据
常用的数据库介绍
A.大型数据库
Oracle公司是最早开发关系数据库的厂商之一,其产品支持最广泛的操作系统平台。目前Oracle关系数据库产品的市场占有率名列前茅。
IBM的DB2是第一个具备网上功能的多媒体关系数据库管理系统,支持包括Linux在内的一系列平台。
B.中型数据库
SQLServer是微软开发的数据库产品,主要支持windows平台。
C.小型数据库
mysql是一个小型关系型数据管理系统,开发者为瑞典mysql AB公司,2005年被sun公司收购。开放 源码。
D.基于嵌入式Linux的数据库(微型数据库)
<1>.基于嵌入式linux的数据库主要有SQLite,Firbird,Berkeley DB,extremeDB
<2>.Firebird是关系型数据库,功能强大,支持存储过程、SQL兼容等
<3>. SQLite关系型数据库,体积小,支持 ACID(原子性、一致性、独立性及持久性 Atomicity、Consistency、Isolation、Durability)事物。
<4>.Berkeley DB中并米有数据库服务器的概念,它的程序库直接连接到应用程序中
<5>.extremeDB是内存数据库,运行效率高 ??
sqlite数据库
是一款轻型的数据库。它的设计目标是嵌入式的,而且目前已经在很多嵌入式产品中使用它,它占用资源非常低,在嵌入式设备中,
可能只需要几百K的内存就够了。它能够支持Windows/Linux/Unix等主流操作系统,同时能够跟很多程序语言相结合,如c/c++,java,php,python等;
sqlite 数据库支持的指令(以"."开头)
以";"结尾的sql语句 (大部分数据库都支持)
增,删,改,查
特点:
1.零配置
2.支持数据库大小至2TB
3.足够小,大致13万行C代码。4.43M
4.源码完全开源
5.简单轻松的API
……
1.下载安装sqlite3数据库
sudo apt-get update
//更新软件源
sudo apt-get install sqlite3
//下载并安装sqlite3,数据库
sudo apt-get install libsqlite3-dev
//安装sqlite3的库
下载源码后执行
./configure --prefix=/home/fs/Downloads/bin
指定安装目录
make install
2.sqlite中的数据类型
sqlite数据库中的数据一般由以下几种常用的数据类型组成
NULL :标识一个NULL值
integer:整数类型 int
real:浮点数 float,double
text:字符串
“ ”
或
‘ ’
char:字符
‘ ’
sql语句 所有数据库通用语句
sqlite 提供的编程接口
3.创建数据库
$ sqlite3 test.db
SQLite version 3.7.15.2 2013-01-09 11:53:05
Enter
".help" for instructions
Enter SQL statements terminated with a
";"
sqlite>
(1)进入到此界面可以输入
sqlite>
.help 寻求帮助
(2)一旦数据库创建好之后
可以使用.database命令检查它是否在数据库列表中
sqlite>
.database
-- --------------- ------------------------------
seq name file
0 main /home/fs/sql/man.db
(3)可以使用.quit退出sqite提示符
sqlite>
.quit
(4)修改mode和header
.mode column 很好的显示模式
.header on 开启标题显示
//补充:
可以在命令提示符中使用 .dump命令来导出完整的数据库在一个文本文件中,如下所示:
$sqlite3 test.db .dump > testDB.sql
上面的命令将转换整个 testDB.db 数据库的内容到 SQLite 的语句中,并将其转储到 ASCII 文本文件 testDB.sql 中。您可以通过简单的方式从生成的 testDB.sql 恢复
$sqlite3 test.db < testDB.sql
4.sqlite创建表
create table table_name(column1 type1, column2 type2, column3 type3……);
- table_name:表名
- columnx:数据表内字段名
- type:字段类型名 字段 字段的类型
eg:
create table if not exists student
(student_name
text, id
text, sex
char , num
integer primary key autoincrement);
//黑色为关键字
当然数据类型也是可以省略!
eg:
create table if not exists student(student_name , id, sex);
//补充:约束
(1)num integer
primary key autoincrement
//可加可不加
(
主键 ) ( 自增 )
主键:每条记录的唯一表示,每个表格只有一个字段可以设置成主键,主键的值不可以为空不可以重复(sqlite可以为空)
(2)not null 指定列不允许为NULL值
create table if not exists student
(student_name
text not NULL, id
text not NULL, sex
char);
(3)default 在insert into 语句没有提供特定的值时,为列提供一个默认值
create table if not exists student
(student_name
text not NULL, id
text not NULL, sex
char,
grade
integer default 99);
(4)unique 约束防止一个特定的列存在两个相同的值
create table if not exists student
(student_name
text not NULL unique, id
text not NULL,
sex
char);
(5)check 约束 启用输入一条记录要检查值的条件。如果条件值为false,则记录违反了约束,且不能输入到表
create table if not exists
student
(
student_name
text not NULL,
id
text not NULL,
sex
char,
grade
integer check(
grade
> 0));
查看表结构
创建好表后可以使用.schema命令查看表的结构
sqlite>
.schema
查看表名
创建好表后可以使用.tables命令查看数据库内所有的表
sqlite>
.tables
5.sqlite删除表
drop table table_name;
sqlite>
drop table student;
6.向表中添加纪录
insert into table_name(column1, column2, column3) values(val1, val2, val3);
insert into student(student_name, id, sex) values ('z3', '123', 'm');
或者
insert into student values('z3', '123', 'm');
7.查询数据记录
select columns
from table_name
[where experssion];
如果您想获取所有可用的字段,那么可以使用下面的语法:
select * from table_name;
如果只想获取 student 表中指定的字段,则使用下面的查询:
select name,id from student;
a.查询输出所有数据记录
select * from table_name;
b.限制输出数据记录数量
select * from table_name limit val;
c.升序输出数据记录
select * from table_name order by column asc;
d.降序输出数据记录
select * from table_name order by column desc;
e.条件查询
select * from table_name where expression;
select * from table_name where column in ('val1', 'val2', 'val3');
{
sqlite> select * from student where name in ("xiaoming", "xiaofang");
name grade id sex
---------- ---------- ---------- ----------
xiaoming 1 110 M
xiaofang 1 119 W
}
select * from table_name where column = 'val1' or column = 'val2';
{
sqlite> select * from student where name="xiaoming" or name="xiaofang";
name grade id sex
---------- ---------- ---------- ----------
xiaoming 1 110 M
xiaofang 1 119 W
sqlite> select * from student where grade=1 and sex='M';
name grade id sex
---------- ---------- ---------- ----------
xiaoming 1 110 M
}
select * from table_name where column between val1 and val2;
{
sqlite> select * from student where id between 114 and 11806 order by id desc;
name grade id sex
---------- ---------- ---------- ----------
xiaofan 2 11806 M
xiaolan 1 120 W
xiaofang 1 119 W
xiaoqi 2 114 M
}
select * from people where age>=10 and age <=15;
select name, age from people where age>= 10 and age<=15;
select * from table_name where column like 'xx%' or 'xxx_';
百分号(%)代表零个、一个或者多个数字或字符 (*)
下划线(_)代表一个单一数字或字符 (?)
{
sqlite> select * from student where name like 'xiao%';
name grade id sex
---------- ---------- ---------- ----------
xiaoming 1 110 M
xiaolan 1 120 W
xiaofang 1 119 W
xiaoqi 2 114 M
xiaofan 2 11806 M
sqlite> select * from student where name like 'xiao_';
sqlite> select * from student where id like '11_';
name grade id sex
---------- ---------- ---------- ----------
xiaoming 1 110 M
xiaofang 1 119 W
xiaoqi 2 114 M
}
8.修改数据记录
update table_name set column1=val1, column2=val2 where expression;
where是sql语句中用于条件判断的命令,expression为判断表达式
例,修改学生信息表学号为0001的数据记录:
update student_info set id=0002, name=hencai where id=0001;
更新
表名 设置 字段名 字段名 当 时
9.在表中添加字段
sqlite>alter table <table_name> add column <field> <type>;
alter table stu add column age integer;
10.删除数据记录
delete from table_name [where expression];
不加判断条件则清空所有数据记录
eg:
delete from stu where id=123;
//删除这一行
11.删除指定字段
step1:alter table info rename to temp;
//备份为temp id , name , age , sex
step2:create table info(id, name, age);
// 创建新表
step3:insert into info select id, name, age from temp;//
导出到新表
练习:
1.创建一个员工的数据库,
2.在里面添加新的数据表,
表中包含姓名,工号,薪水(salary)……
3.向数据表中添加几个数据
4.练习查询
5.添加表项性别,年龄字段
6.更新数据库员工的年龄信息
7.删除工号为***的员工
8.备份数据库资料