查找树,俄罗斯方块,系统编程开始
This commit is contained in:
35
Chapter11/ds/tree/retrieval/Makefile
Normal file
35
Chapter11/ds/tree/retrieval/Makefile
Normal file
@@ -0,0 +1,35 @@
|
|||||||
|
# 方便起见一般都会先定义编译器链接器
|
||||||
|
CC = gcc
|
||||||
|
LD = gcc
|
||||||
|
|
||||||
|
# 正则表达式表示目录下所有.c文件,相当于:SRCS = main.c a.c b.c
|
||||||
|
SRCS = $(wildcard *.c)
|
||||||
|
|
||||||
|
# OBJS表示SRCS中把列表中的.c全部替换为.o,相当于:OBJS = main.o a.o b.o
|
||||||
|
OBJS = $(patsubst %c, %o, $(SRCS))
|
||||||
|
|
||||||
|
# 可执行文件的名字
|
||||||
|
TARGET = main
|
||||||
|
|
||||||
|
# .PHONE伪目标,具体含义百度一下一大堆介绍
|
||||||
|
.PHONY:all clean
|
||||||
|
|
||||||
|
# 要生成的目标文件
|
||||||
|
all: $(TARGET)
|
||||||
|
|
||||||
|
LDFLAGS=-L/usr/local/lib
|
||||||
|
|
||||||
|
# LDLIBS=-lqueue -lllist
|
||||||
|
|
||||||
|
# 第一行依赖关系:冒号后面为依赖的文件,相当于Hello: main.o a.o b.o
|
||||||
|
# 第二行规则:$@表示目标文件,$^表示所有依赖文件,$<表示第一个依赖文件
|
||||||
|
$(TARGET): $(OBJS)
|
||||||
|
$(LD) $(LDFLAGS) -o $@ $^ $(LDLIBS)
|
||||||
|
|
||||||
|
# 上一句目标文件依赖一大堆.o文件,这句表示所有.o都由相应名字的.c文件自动生成
|
||||||
|
%.o:%.c
|
||||||
|
$(CC) -c $^
|
||||||
|
|
||||||
|
# make clean删除所有.o和目标文件
|
||||||
|
clean:
|
||||||
|
rm -f $(OBJS) $(TARGET)
|
||||||
121
Chapter11/ds/tree/retrieval/trie.c
Normal file
121
Chapter11/ds/tree/retrieval/trie.c
Normal file
@@ -0,0 +1,121 @@
|
|||||||
|
#include <stdio.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
#define DESC_SIZE 256
|
||||||
|
#define KEY_SIZE 256
|
||||||
|
#define BUFSIZE 512
|
||||||
|
#define FNAME "log"
|
||||||
|
|
||||||
|
struct node_st
|
||||||
|
{
|
||||||
|
struct node_st *ch[26];
|
||||||
|
char desc[DESC_SIZE];
|
||||||
|
};
|
||||||
|
|
||||||
|
static int get_word(FILE *fp, char *key, char *desc)
|
||||||
|
{
|
||||||
|
char buf[BUFSIZE];
|
||||||
|
char *retp;
|
||||||
|
int i, j;
|
||||||
|
|
||||||
|
retp = fgets(buf, BUFSIZE, fp);
|
||||||
|
if (NULL == retp)
|
||||||
|
return -1;
|
||||||
|
|
||||||
|
for (i = 0; i < KEY_SIZE - 1 && buf[i] != ':'; i++)
|
||||||
|
key[i] = buf[i];
|
||||||
|
key[i] = '\0';
|
||||||
|
|
||||||
|
i++;
|
||||||
|
|
||||||
|
for (j = 0; j < DESC_SIZE - 1 && buf[i] != '\0'; j++, i++)
|
||||||
|
desc[j] = buf[i];
|
||||||
|
desc[j] = '\0';
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static struct node_st *newnode()
|
||||||
|
{
|
||||||
|
struct node_st *node;
|
||||||
|
int i;
|
||||||
|
|
||||||
|
node = malloc(sizeof(*node));
|
||||||
|
if (NULL == node)
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
node->desc[0] = '\0';
|
||||||
|
|
||||||
|
for (i = 0; i < 26; i++)
|
||||||
|
node->ch[i] = NULL;
|
||||||
|
|
||||||
|
return node;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int insert(struct node_st **root, char *key, char *desc)
|
||||||
|
{
|
||||||
|
if (NULL == *root)
|
||||||
|
{
|
||||||
|
*root = newnode();
|
||||||
|
if (NULL == *root)
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if ('\0' == *key)
|
||||||
|
{
|
||||||
|
strcpy((*root)->desc, desc);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
return insert((*root)->ch + *key - 'a', key + 1, desc);
|
||||||
|
}
|
||||||
|
|
||||||
|
static char *find(struct node_st *root, char *key)
|
||||||
|
{
|
||||||
|
if (NULL == root)
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
if ('\0' == *key)
|
||||||
|
return root->desc;
|
||||||
|
|
||||||
|
return find(root->ch[*key - 'a'], key + 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
int main()
|
||||||
|
{
|
||||||
|
struct node_st *tree;
|
||||||
|
FILE *fp;
|
||||||
|
char desc[DESC_SIZE] = {'\0'}, key[KEY_SIZE] = {'\0'};
|
||||||
|
int ret;
|
||||||
|
char *datap;
|
||||||
|
|
||||||
|
fp = fopen(FNAME, "r");
|
||||||
|
if (NULL == fp)
|
||||||
|
{
|
||||||
|
fprintf(stderr, "fopen():error!\n");
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
while (1)
|
||||||
|
{
|
||||||
|
ret = get_word(fp, key, desc);
|
||||||
|
if (-1 == ret)
|
||||||
|
break;
|
||||||
|
|
||||||
|
// puts(key);
|
||||||
|
// puts(desc);
|
||||||
|
|
||||||
|
insert(&tree, key, desc);
|
||||||
|
}
|
||||||
|
|
||||||
|
datap = find(tree, "donkey");
|
||||||
|
if (NULL == datap)
|
||||||
|
printf("Can not find!\n");
|
||||||
|
else
|
||||||
|
puts(datap);
|
||||||
|
|
||||||
|
fclose(fp);
|
||||||
|
|
||||||
|
exit(0);
|
||||||
|
}
|
||||||
@@ -88,8 +88,14 @@
|
|||||||
- 广义表
|
- 广义表
|
||||||
|
|
||||||
`( root ( left ) ( right) )`,进行嵌套。
|
`( root ( left ) ( right) )`,进行嵌套。
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
- 搜索树
|
||||||
|
|
||||||
|
空间换时间,查找是**o(1)**。
|
||||||
|
|
||||||
|
**课后作业:词频统计**
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
14
Chapter12/C12-俄罗斯方块.md
Normal file
14
Chapter12/C12-俄罗斯方块.md
Normal file
@@ -0,0 +1,14 @@
|
|||||||
|
# 俄罗斯方块
|
||||||
|
|
||||||
|
1. 图形
|
||||||
|
|
||||||
|
ANSI_VT,framebuffer
|
||||||
|
|
||||||
|
前者以光标为单位,后者以像素为单位。
|
||||||
|
|
||||||
|
推荐后者。
|
||||||
|
|
||||||
|
2. 输入设备
|
||||||
|
|
||||||
|
3. 并发
|
||||||
|
|
||||||
10
Chapter12/ansi_vt.c
Normal file
10
Chapter12/ansi_vt.c
Normal file
@@ -0,0 +1,10 @@
|
|||||||
|
#include <stdio.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
|
||||||
|
int main()
|
||||||
|
{
|
||||||
|
// 以"\033"开头
|
||||||
|
printf("\033[2J\033[1;1H\033[31;4mhello\n\033[0m");
|
||||||
|
|
||||||
|
exit(0);
|
||||||
|
}
|
||||||
36
Chapter13/C13-Linux系统编程学习笔记.md
Normal file
36
Chapter13/C13-Linux系统编程学习笔记.md
Normal file
@@ -0,0 +1,36 @@
|
|||||||
|
# I/O操作
|
||||||
|
|
||||||
|
输入输出是一切实现的基础。
|
||||||
|
|
||||||
|
标准IO:`stdio`
|
||||||
|
|
||||||
|
系统调用IO(文件IO):`sysio`
|
||||||
|
|
||||||
|
优先使用标准IO,兼容性更好,还有合并系统调用的优势。
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
```c
|
||||||
|
/* stdio */
|
||||||
|
/* FILE类型贯穿始终 */
|
||||||
|
|
||||||
|
FILE *fopen(const c);
|
||||||
|
fclose();
|
||||||
|
|
||||||
|
fgetc();
|
||||||
|
fputc();
|
||||||
|
fgets();
|
||||||
|
fputs();
|
||||||
|
fread();
|
||||||
|
fwrite();
|
||||||
|
|
||||||
|
printf();
|
||||||
|
scanf();
|
||||||
|
|
||||||
|
fseek();
|
||||||
|
ftell();
|
||||||
|
rewind();
|
||||||
|
|
||||||
|
fflush();
|
||||||
|
```
|
||||||
|
|
||||||
52
Chapter13/C13-Linux系统编程项目实战.md
Normal file
52
Chapter13/C13-Linux系统编程项目实战.md
Normal file
@@ -0,0 +1,52 @@
|
|||||||
|
# 项目前瞻
|
||||||
|
|
||||||
|
基于IPV4的流媒体广播系统。
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
## 项目需求
|
||||||
|
|
||||||
|
需要基于客户机和服务器模型的网络音频广播/点播系统。
|
||||||
|
|
||||||
|
用于语音教室和公共广播。
|
||||||
|
|
||||||
|
分为服务器和客户机,服务器在PC上运行,客户机在PC机或者嵌入式设备。
|
||||||
|
|
||||||
|
服务器可以向局域网内以多播的方式给所有客户机发送数据,客户机自己选择接收数据。
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
## 简要框图
|
||||||
|
|
||||||
|
<img src="https://s2.loli.net/2024/04/25/kpolhzmgBEcSYxM.png"/>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
## 参考书目
|
||||||
|
|
||||||
|
1. UNIX环境高级编程(第一版经典,第二版有错误)
|
||||||
|
2. UNIX网络编程
|
||||||
|
3. TCP/IP详解(卷一)
|
||||||
|
4. 深入理解计算机系统
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
## 知识网络
|
||||||
|
|
||||||
|
- I/O操作(参考书目1:3,5章,14章非阻塞IO)
|
||||||
|
- 文件系统(参考书目1:4,6,7章)
|
||||||
|
- 并发(信号10章,多线程10,11章)
|
||||||
|
- IPC(进程间通信,8章进程基础,13章守护进程)
|
||||||
|
- 进程间通信(15,16章)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
## 注意事项
|
||||||
|
|
||||||
|
1. 弃用root用户
|
||||||
|
2. 重构
|
||||||
|
3. 课堂重点:项目,课堂代码,面试题,实验性题目,推荐书籍的课后题
|
||||||
29
Chapter13/io/stdio/fopen.c
Normal file
29
Chapter13/io/stdio/fopen.c
Normal file
@@ -0,0 +1,29 @@
|
|||||||
|
#include <errno.h>
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
int main()
|
||||||
|
{
|
||||||
|
FILE *fp;
|
||||||
|
|
||||||
|
fp = fopen("tmp", "r");
|
||||||
|
if (NULL == fp)
|
||||||
|
{
|
||||||
|
// fprintf(stderr, "fopen() failed! errno = %d\n", errno);
|
||||||
|
// out: fopen() failed! errno = 2
|
||||||
|
/* errno:定义路径 /usr/include/asm-generic/errno-base.h */
|
||||||
|
|
||||||
|
// perror("fopen()");
|
||||||
|
// out: fopen(): No such file or directory
|
||||||
|
|
||||||
|
fprintf(stderr, "fopen(): %s\n", strerror(errno));
|
||||||
|
// out: fopen(): No such file or directory
|
||||||
|
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
puts("OK!");
|
||||||
|
|
||||||
|
exit(0);
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user