head/tail实现
typedef struct
{
int rio_fd;
int rio_cnt;
char *rio_bufptr;
char rio_buf[RIO_BUFFSIZE];
}rio_t; void rio_readinitb(rio_t *rp, int fd)
{
rp->rio_fd = fd;
rp->rio_cnt = ;
rp->rio_bufptr = rp->rio_buf;
} ssize_t rio_read(rio_t *rp, void *usrbuf, size_t n)
{
int cnt = ; while (rp->rio_cnt <= )
{
if ((rp->rio_cnt = read(rp->rio_fd, rp->rio_buf, sizeof(rp->rio_buf))) < )
{
if (errno != EINTR)
{
return -;
}
}
else if (rp->rio_cnt == )
{
return ;
}
else
{
rp->rio_bufptr = rp->rio_buf;
}
} //cnt = n > rp->rio_cnt?rp->rio_cnt:n; cnt = n;
if (n > rp->rio_cnt)
{
cnt = rp->rio_cnt;
} memcpy(usrbuf, rp->rio_bufptr, cnt);
rp->rio_cnt -= cnt;
rp->rio_bufptr += cnt; return cnt;
} ssize_t rio_readlineb(rio_t *rp, void *usrbuf, size_t maxlen, int count)
{
int i = , rc = , num = ;
char c = , *buf = usrbuf; lseek(rp->rio_fd, maxlen, SEEK_END); for (i = ; i < maxlen; i++)
{
if ((rc = rio_read(rp, &c, )) == )
{
*buf++ = c;
if (c == '\n')
{
if (++num == count)
{
break;
}
}
}
else if (rc == )
{
if (i == )
{
return ;
}
else
{
break;
}
}
else
{
return -;
}
} *buf = '\0';
return i;
}
二、head命令实现
#include <stdio.h>
#include <stdlib.h>
#include <fcntl.h>
#include <unistd.h>
#include <string.h>
#include "rio.h" #define MAXSIZE 4096 int main(int argc, char **argv)
{
if (argc < )
{
fprintf(stderr, "usage %s [-n n] filename\n", argv[]);
return -;
} int times = , i = , in_fd = -, n_char = ;
char filename[] = {};
char buf[MAXSIZE] = {};
rio_t rio_buf = {}; for (i = ; i < argc; i++)
{
if (!strcmp(argv[i], "-n"))
{
times = atoi(argv[++i]);
}
else
{
snprintf(filename, sizeof(filename), "%s", argv[i]);
}
} if ((in_fd = open(filename, O_RDONLY)) == -)
{
fprintf(stderr, "open %s failed\n", filename);
return -;
} rio_readinitb(&rio_buf, in_fd);
if ((n_char = rio_readlineb(&rio_buf, buf, MAXSIZE, times)) > )
{
write(STDOUT_FILENO, buf, n_char);
} close(in_fd); return ;
}
三、tail命令实现
#include "rio.h" #define MAXSIZE 4096 void show_info(char *buf, char **ptr, int count); int main(int argc, char **argv)
{
if (argc < )
{
fprintf(stderr, "usage %s [-n n] filename\n", argv[]);
return -;
} int times = , i = , in_fd = -;
char filename[] = {};
char buf[MAXSIZE] = {};
rio_t rio_buf = {};
char *ptr[MAXSIZE]; for (i = ; i < argc; i++)
{
if (!strcmp(argv[i], "-n"))
{
times = atoi(argv[++i]);
}
else
{
snprintf(filename, sizeof(filename), "%s", argv[i]);
}
} if ((in_fd = open(filename, O_RDONLY)) == -)
{
fprintf(stderr, "open %s failed\n", filename);
return -;
} rio_readinitb(&rio_buf, in_fd);
rio_read(&rio_buf, buf, MAXSIZE); show_info(buf, ptr, times); return ;
} void show_info(char *buf, char **ptr, int times)
{
int num = ;
int flag = ; if (num < times)
{
*ptr = strrchr(buf, '\n');
flag = ;
**ptr = '\0';
show_info(buf, ptr + , --times);
} if (flag)
{
printf("%s\n", *ptr + );
}
}
通过递归show_info来实现按顺序打印,其实也可以用链表来实现,不过递归写起来简单。
head/tail实现的更多相关文章
- REDHAT一总复习1 输出重定向及head tail的用法
1.使用bash命令,在server机上完成以下任务.(考点是:head tail的使用) .显示/usr/bin/clean-binary-files文件的前12行,并将其输出到/home/stu ...
- tail命令详解
搜索 纠正错误 添加实例 tail 在屏幕上显示指定文件的末尾若干行 补充说明 tail命令 用于输入文件中的尾部内容.tail命令默认在屏幕上显示指定文件的末尾10行.如果给定的文件不止一个,则在 ...
- Linux命令详解之—tail命令
tail命令也是一个非常常用的文件查看类的命令,今天就为大家介绍下Linux tail命令的用法. 更多Linux命令详情请看:Linux命令速查手册 Linux tail命令主要用来从指定点开始将文 ...
- linux命令之tail
tail用于输出文件末尾部分.一个比较有用的功能是tail + grep实现类似于安卓开发时调试使用的logcat,具体操作是: 一般我是用SecureCRT连接linux,然后使用SecureCRT ...
- PHP实现linux命令tail -f
PHP实现linux命令tail -f 今天突然想到之前有人问过我的一个问题,如何通过PHP实现linux中的命令tail -f,这里就来分析实现下. 这个想一想也挺简单,通过一个循环检测文件,看文件 ...
- tail -f 和 -F 的用法
tail -f 和 -F 的用法 Tai 2010-08-16 16:03:18 -f 是--follow[=HOW]的缩写, 可以一直读文件末尾的字符并打印出来."[=HOW]" ...
- scala tail recursive优化,复用函数栈
在scala中如果一个函数在最后一步调用自己(必须完全调用自己,不能加其他额外运算子),那么在scala中会复用函数栈,这样递归调用就转化成了线性的调用,效率大大的提高.If a function c ...
- linux head、tail、sed、cut、grep、find
head用法: head 参数 文件名 -cn:显示前n个字节 -n:显示前n行 例子:head -c20 1.txt 显示1.txt文件中前20个字符 ls | head -20:显示前20 ...
- linux命令每日一练习-tail
tail 是查看文件的末尾 tail -n 5*** 显示文件×××的最后5行 tail -n +5 ××× 显示文件×××从第5行开始的内容 tail -f *** 监视文件×××的末尾.循环展示
随机推荐
- hibernate一对一外键单向关联
关联是类(类的实例)之间的关系,表示有意义和值得关注的连接. 本系列将介绍Hibernate中主要的几种关联映射 Hibernate一对一主键单向关联Hibernate一对一主键双向关联Hiberna ...
- Oracle数据库操作知道
SELECT TGTID,PHONENUM,REGISTERDATE ,to_date(REGISTERDATE,'YYYY-MM-DD HH24:MI:SS') AS T FROM WTRESSEN ...
- MVC视图展现模式之移动布局解析-续集
网站就必须用响应式布局吗?MVC视图展现模式之移动布局:http://www.cnblogs.com/dunitian/p/5213787.html demo:http://pan.baidu.com ...
- 关于for循环中,定义的i的作用域的问题。
for(var i=0;i<2;i++){ console.log(i) } console.log(i) 经过测试:在IE9+,谷歌,火狐中.都出现了0,1,2三个值. 所以其作用域在整个上下 ...
- ASP.NET MVC5+EF6+EasyUI 后台管理系统(21)-权限管理系统-跑通整个系统
系列目录 这一节我们来跑通整个系统,验证的流程,通过AOP切入方式,在访问方法之前,执行一个验证机制来判断是否有操作权限(如:增删改等) 原理:通过MVC自带筛选器,在筛选器分解路由的Action和c ...
- 理清JavaScript正则表达式--上篇
在JavaScript中,正则表达式由RegExp对象表示.RegExp对象呢,又可以通过直接量和构造函数RegExp两种方式创建,分别如下: //直接量 var re = /pattern/[g | ...
- Python(五)模块
本章内容: 模块介绍 time & datetime random os sys json & picle hashlib XML requests ConfigParser logg ...
- NGUI学习笔记(一)UILabel介绍
来个前言: 作为一个U3D程序员,自然要写一写U3D相关的内容了.想来想去还是从UI开始搞起,可能这也是最直观同时也最重要的部分之一了.U3D自带的UI系统,也许略坑,也没有太多介绍的价值,那么从今天 ...
- Angular2 小贴士-多级注入器
angular2 的依赖注入包含了太多的内容,其中的一个重点就是注入器,而注入器又非常难理解,今天我们不深入介绍注入器的内容,可以参考官方文档,我们今天来说注入器的层级. 也就是组件获取服务的容器会选 ...
- 定向爬虫 - Python模拟新浪微博登录
当我们试图从新浪微博抓取数据时,我们会发现网页上提示未登录,无法查看其他用户的信息. 模拟登录是定向爬虫制作中一个必须克服的问题,只有这样才能爬取到更多的内容. 实现微博登录的方法有很多,一般我们在模 ...