该代码功能实现对不同设备号的分别统计,统计内容为不同设备号上两次相邻读访问的时间间隔,代码分两步

step1,生成对应设别号的访问时间文件,比如newweb的trace中有0,1,2三个设备,则生成newweb0.cvs;newweb1.cvs;newweb2.cvs三个文件。

step2,计算三个文件的中两两项的时间间隔,生成Renewweb0.cvs;Renewweb1.cvs;Renewweb2.cvs(生成.cvs的后缀的目的是为了方便excel画图)


写代码过程几点总结

1.我调试再windows底下调试的,当时遇到fopen函数无法打开文件,原因是window文件显示隐含了后缀名,fopen("d:\\text.txt","r"); 我电脑上看到的为text.txt,而实际文件名是test.txt.txt

2.window下文件名字太长,打不开。后来我把文件名字改短了,就打开了,不知道为啥

3.linux下fopen函数使用 fopen(filename,"a");生成新文件时,filename只能为同级目录下,filename="./test"或者filename="test"可以在该目录下生成新文件;但是filename="dir/test"就不一定了,若在代码运行目录下,dir目录已经存在,则可以在dir目录下生成test文件,若dir目录不存在,则创建失败。原因是fopen(filename,"a"),只能创建已知目录下的文件,而不能创建目录。

4.sting类型转化为int float等都有对应函数,int转化成string也有。另外strcat,strcpy等函数常用

5.char filename[]="name1"; char filename1[]="name2";则filename和filename1回申请到同一片空间。filename1和filename的改变会相互影响。方法是char *加上边界char filename[20]="name1"; char filename1[20]="name2";

6 windows底下运行,申请浮点类型会报错,说什么连接问题啊什么的,float f;方法f复制且,加一个指针指向它;即float f=0.0,*p=&f;这样就ok了

7 linux底下运行时报段,栈溢出错误,"stack smahing detecte..."我的问题是类似于char filename[]="name1"都没有加上边界,改为char filename[20]="name1"就好了。

8关于段错误的原因,段错误的原因有如下:(1)以只读方式打开的文件不存在,包括路径中的目录不存在以及路径存在但文件不存在,你可能粗心把文件名写错了。(2)数组申请空间小了。比如int b[20]; 但是在代码运行过程中,你使用到了b[21]等。段错误主要原因就是你使用到了不存在的东西。

9关于fgets函数。fgets(buf,512,f); 这个函数每次至多取一行的内容到buf里面,若这一行只有400个char,函数并不会取下一行内容。但若这一行有600个char,则下次取得时候会接在这一行的后面去取。

10关于sprintf函数,该函数同printf一样使用,只是printf是把字符串打印在屏幕上,而sprintf函数可以把字符串打印在字符串中。故用法

 sprintf(filename,"/home/code/%s-D%s",argv[1],argv[2]);

sprintf(filename1,"/home/%s",name);

这两种方法都ok,反正想想屏幕上会输出什么,则filename中会有什么。

11关于sscanf。

   该函数会把空格自动识别为一个%s ,如sscanf("123 er 324 4sd","%s%s%s",buf1,buf2,buf3)则三个buf中的内容分别是buf1="123"   buf2="er"  buf3="324" 。注意如果把空格换成逗号,则buf1="123,er,324,4sd"  而buf2   buf3没有读入sscanf("123,er,324,4sd","%[^,],%[^,],%[^,]",buf1,buf2,buf3)来实现读入。具体表达式看网上的sscanf用法详解,反正这个函数支持各种正则表达式,挺强大的。一开始我不知道有这样一个函数,所以代码中用的截取字段的函数,其实完全可以通过sscanf函数来实现。

注意sscanf若放在 int dev_num;中则要取地址,同scanf,

另外利用sscanf的返回值可以成功处理最后的几个多余的回车,实现正确的读入,而不会多读入一行。sscanf返回读取的元素个数,若是回车,则返回-1

while(fgets(StrLine,512,f)!=NULL)

      if(1==sscanf(StrLine,%f,&time))

         /*执行代码..这样通过返回值就可以避免读回车行*/

}

另外fscanf和sscanf原理相同,也可以利用返回值。如:

while(5==fscanf(pfile,"%d,%ld,%ld,%[^,],%lf",&dev,&offset,&length,rw,&time))其中pfile为pfile=fopen("/home/trace.csv","r");


代码如下

/*中间文件dev0,dev1等等只得到一列,全是时间*/
#include"stdio.h"
#include"string.h"
#define SectorSize 512
#include"stdlib.h"
int total_dev_num=0;
 
char * split(char *dst,char *src, int n,int m) /*n为长度,m为位置,进行字符串的截取*/
{
    char *p = src;
    char *q = dst;
    int len = strlen(src);
    if(n>len) n = len-m;    /*从第m个到最后*/
    if(m<0) m=0;    /*从第一个开始*/
    if(m>len) return NULL;
    p += m;
    while(n--) *(q++) = *(p++);
    *(q++)='\0';
    return dst;/*得到目标字符串*/
}
/*进行每次访问时间按设备号存放在不同文件中*/
int collect_time_sector(int dev_num,long offset,long length,float time,char *argv)
{
FILE *time_sector;
int j=0,len;
char filename[30];
char str[10];
     if(dev_num>total_dev_num)total_dev_num=dev_num;
strcpy(filename,argv);
sprintf(str,"%d",dev_num);
strcat(filename,str);
strcat(filename,".csv");
/*printf("%s\n",filename);*/
/*printf("%s",filename);*/
if((time_sector=fopen(filename,"a"))==NULL)
{
printf("error!000");
return -1;
}
fprintf(time_sector,"%f\n",time);/*该设备访问的时间*/
fclose(time_sector);
return 0;
}
 
void dealStrLine(char* string,char *argv)/*解析每一行的内容*/
{
int i=0,j=0;
int n=0,m=0,dev_num;
char RoW[10];
long  length;
long offset;
float time=0.0,*point=&time;
char dst[64];
char *stopstring;
while(string[i]!='\0')
{   
n++;
if(string[i]==',')
{
j++;
split(dst,string,n-1,m);
switch (j)
{
case 1:{dev_num=atoi(dst);break;}
case 2:{offset=strtol(dst,&stopstring,10);break;}
case 3:{length=strtol(dst,&stopstring,10);break;}
case 4:{strcpy(RoW,dst);break;}
default:printf("default");
}
n=0;
m=i+1;
}
i++;
}
split(dst,string,n-1,m);
time=atof(dst);
if((!strcmp(RoW,"R"))||(!strcmp(RoW,"r")))
collect_time_sector(dev_num,offset,length,time,argv);
}
 
int interval_time(char * argv)/*计算间隔时间*/
{
FILE *source,*result;
char filename[30];
char filename1[30];
char StrLine[512];
char *stopstring,str[10];
int i,len;
float time=0.0,lasttime=0.0,*point=&time;
for(i=0;i<=total_dev_num;i++)
{
sprintf(str,"%d",i);
 
strcpy(filename,argv);
strcat(filename,str);
strcat(filename,".csv");
 
strcpy(filename1,"Re");
 
strcat(filename1,argv);
strcat(filename1,str);
strcat(filename1,".csv");
 
if((source=fopen(filename,"r"))==NULL)
{
printf("error11!");
return -1;
}
if((result=fopen(filename1,"a"))==NULL)
{
printf("error22!");
return -1;
}
fgets(StrLine,128,source);
lasttime=atof(StrLine);
while(!feof(source))
{
fgets(StrLine,128,source);
time=atof(StrLine);
fprintf(result,"%f\n",time-lasttime);
lasttime=time;
}
fclose(source);
fclose(result);
}
return 0;
}
 
int main(int argc,char *argv[])
{
FILE *source,*outcome;
float time;
char filename[20];
char StrLine[512];
strcpy(filename,argv[1]);
outcome=fopen("./outcome.spc","a");
if((source=fopen(filename,"r"))==NULL)
{
printf("error!333");
return -1;
}
while(!feof(source))
{
fgets(StrLine,1024,source);
dealStrLine(StrLine,argv[1]);
/* printf("%s\n",StrLine);*/
fprintf(outcome,"%s\n",StrLine);
}
fclose(outcome);
fclose(source);
interval_time(argv[1]);
printf("finish!\n");
return 0;
}

再gcc下编译生成运行文件s1,即gcc *.c -o s1

关于脚本文件

#!/bin/sh
./s1 text.txt
./s1 newweb-2
 

个脚本分析text.txt和newweb-2两个trace

Host by is-Programmer.com | Power by Chito 1.3.3 beta | Theme: Aeros 2.0 by TheBuckmaker.com