How should one read a book?

本文探讨了如何更好地阅读书籍,尤其是小说。作者建议读者应该摒弃成见,全身心地投入到书中,尝试理解作者的意图并与其共同创作。通过广泛开放的心态,读者能够捕捉到作品中微妙的细节,从而更深刻地理解整部作品。

It is simple enough to say that since books have classes—fiction , biography, poetry—we should separate them and take from each what it is right that each should give us. Yet few people ask from books what books can give us. Most commonly we come to books with blurred and divided minds, asking of fiction that it shall be true, of poetry that it shall be false, of biography that it shall be flattering, of history that it shall enforce our own prejudices. if we could drive away all such preconceptions when we read, that would be an admirable beginning. Do not dictate to your author; try to become him. Be his fellow-worker. If you hang back, and reserve and criticize at first, you are preventing yourself from getting the fullest possible value from what you read. But if you open your mind as widely as possible, then signs and hints of almost imperceptible fineness, from the twist and turn of the first sentences, will bring you into the presence of a human being unlike any other. Steep yourself in this, acquaint yourself with this, and soon you will find that tour author is giving you, or attempting to give you, something far more definite. The thirty-two chapters of a novel—if we consider how to read a novel first—are an attempt to make something as formed and controlled as a building; but words are more abstract than bricks; reading is a longer and more complicated process than seeing. Perhaps the quickest way to understand the elements of what a novelist is doing is not read, but to write; to make your own experiment with the dangers and difficulties of words. Recall, then, some event that has left a distinct impression on you—how at the corner of the street, perhaps, you passed two people talking A tree shook; an electric light danced; the tone of the talk was comic, but also tragic; a whole vision, an entire conception, seemed contained in that moment.
To read a novel is a difficult and complex art. you must be capable not only of great skill of perception, but of great boldness of imagination if you are going to make use of all that the novelist—the great artist—gives you.

<think> 我们将在xv6中实现一个简单的UNIX find程序。程序将递归遍历目录树,查找所有具有指定文件名的文件。 步骤: 1. 参考user/ls.c,了解如何读取目录。 2. 使用递归处理子目录,但跳过"."和".."。 3. 使用C字符串和strcmp()进行字符串比较。 4. 将程序添加到Makefile的UPROGS中。 程序框架: - 主函数:处理命令行参数,从指定目录开始递归(默认为当前目录) - 递归函数:遍历目录中的每个条目,如果是文件且匹配则打印路径;如果是目录(且不是"."或".."),则递归进入 注意: - 文件系统操作:使用open, read, close等系统调用。 - 目录条目结构:参见xv6的dirent结构(kernel/fs.h)。 我们将编写以下代码: </think> # xv6系统实现UNIX find程序 我将指导你实现一个简单版本的UNIX find程序,用于在xv6文件系统中递归查找指定文件名的文件。这个实现基于xv6的文件系统结构和用户空间工具规范。 ## 实现代码 (user/find.c) ```c #include "kernel/types.h" #include "kernel/stat.h" #include "user/user.h" #include "kernel/fs.h" #include "kernel/fcntl.h" // 递归查找函数 void find(char *path, char *target) { char buf[512]; char *p; int fd; struct dirent de; struct stat st; // 打开路径 if ((fd = open(path, O_RDONLY)) < 0) { fprintf(2, "find: cannot open %s\n", path); return; } // 获取路径状态信息 if (fstat(fd, &st) < 0) { fprintf(2, "find: cannot stat %s\n", path); close(fd); return; } // 处理不同类型文件 switch (st.type) { case T_FILE: // 比较文件名(使用strcmp) if (strcmp(path + strlen(path) - strlen(target), target) == 0) { printf("%s\n", path); } break; case T_DIR: // 构造完整路径 if (strlen(path) + 1 + DIRSIZ + 1 > sizeof buf) { printf("find: path too long\n"); break; } strcpy(buf, path); p = buf + strlen(buf); *p++ = '/'; // 读取目录条目 while (read(fd, &de, sizeof(de)) == sizeof(de)) { if (de.inum == 0) continue; // 跳过"."和".." if (strcmp(de.name, ".") == 0 || strcmp(de.name, "..") == 0) continue; // 构造子路径 memmove(p, de.name, DIRSIZ); p[DIRSIZ] = 0; // 递归查找子目录 find(buf, target); } break; } close(fd); } int main(int argc, char *argv[]) { if (argc != 3) { fprintf(2, "Usage: find <path> <filename>\n"); exit(1); } find(argv[1], argv[2]); exit(0); } ``` ## Makefile修改 在`Makefile`的`UPROGS`部分添加: ```makefile UPROGS=\ ... $U/_find\ ... ``` ## 实现说明 ### 关键数据结构(参考xv6源码) 1. **目录条目结构**(kernel/fs.h): ```c #define DIRSIZ 14 struct dirent { ushort inum; char name[DIRSIZ]; }; ``` 2. **文件状态结构**(kernel/stat.h): ```c #define T_DIR 1 // 目录 #define T_FILE 2 // 文件 #define T_DEVICE 3 // 设备 struct stat { int dev; // 文件系统设备号 uint ino; // inode号 short type; // 文件类型 short nlink; // 链接数 uint64 size; // 文件大小(字节) }; ``` ### 算法流程 ```mermaid graph TD A[开始] --> B[打开路径] B --> C{路径类型} C -->|文件| D[比较文件名] C -->|目录| E[读取目录条目] E --> F{条目类型} F -->|普通文件| G[比较文件名] F -->|目录| H[跳过.和..] H --> I[递归调用find] D -->|匹配| J[打印路径] G -->|匹配| J J --> K[继续处理] K --> L[结束] ``` ### 关键实现细节 1. **路径处理**: - 使用`buf[512]`缓冲区存储完整路径 - 通过指针操作构建路径:`path + "/" + filename` - 检查路径长度避免溢出[^3] 2. **递归控制**: - 跳过特殊目录`.`和`..`(使用`strcmp`比较) - 只处理有效目录条目(`de.inum != 0`) - 深度优先遍历目录树 3. **文件匹配**: - 使用`strcmp`比较目标文件名 - 精确匹配而非模式匹配(如UNIX find的`-name`选项) ## 测试方法 1. 创建测试目录结构: ```bash $ mkdir test $ echo > test/file1 $ mkdir test/subdir $ echo > test/subdir/file2 $ echo > test/subdir/target ``` 2. 执行查找: ```bash $ find / test target /test/subdir/target $ find / test file /test/file1 /test/subdir/file2 ``` 3. 边界测试: ```bash # 查找不存在的文件 $ find / test notfound (无输出) # 无效路径 $ find /invalid/path target find: cannot open /invalid/path ``` ## 性能考虑 1. **递归深度**: - xv6文件系统最大路径长度有限(缓冲区512字节) - 目录嵌套深度受限于路径缓冲区 2. **效率优化**: - 及时关闭文件描述符(避免资源泄漏) - 减少不必要的字符串操作 - 提前终止条件检查 这个实现展示了xv6文件系统的基本操作,包括目录遍历、文件状态检查和路径处理,遵循了UNIX工具的设计哲学。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值