鄙人正在做一个项目,该项目是负责采集网络设备信息的。
项目中有很多种采集任务,其中包括syslog的采集,syslog是通过telnet采集回来并与以前的采集生成的log文件比较,并进行追加。syslog采集一段时间后,cpu占用越来越高。
syslog采集任务 需要进行I/o操作,是n个设备在循环中依次执行这是Syslog任务类:里面收集设备信息,并调用 SyslogFetchingTask.run()进行syslog采集
public class SysLogBackUpTask extends Thread{
   public static PropertiesHandle ph = PropertiesHandle.getPropertiesHandle("ziyuan.properties");   private DataUtil du;
   
   
   
   public SysLogBackUpTask(){
   du = DataUtil.getDataUtil();    start();
   }
   
   
   public void run(){
   
    List<NetRoutInfo> routs = null;
    String timeNum =ph.getProperty("syslogTaskTime");
    timeNum = timeNum==null?"5":timeNum;
    
    Long sleepTime = Long.valueOf(timeNum)*60*1000;//间隔时间     SyslogFetchingTask sft =new SyslogFetchingTask();//syslog采集并分析类
    while(true){      routs = du.getAllRoutByStatus(0);
     System.out.println(routs.size()+"台设备激活,并进行syslog备份");
    
     for(NetRoutInfo rout:routs){
     System.out.println("rout:::"+rout.getRoutName()+"的采集开始");      try{      sft.setRout(rout);
     sft.run();
     Thread.sleep(100);
    
     }catch(Exception e){
     System.out.println(rout.getRoutName()+" ");
     e.printStackTrace();
    
     continue;
     }
     } 
         
     try {
Thread.sleep(sleepTime);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
routs.clear();
    }
   
   }
 
   
}
下面是SyslogFetchingTask.java是syslog采集任务的真正执行者
public class SyslogFetchingTask { private NetRoutInfo rout;
private String fileName;
private String fileContent="";
private HashMap<String,StringBuffer> needAppend;//用于保存每个log文件应追加的内容 key=log文件名  
// value =每个文件应追加的内容
public SyslogFetchingTask(){


}
 

public void setRout(NetRoutInfo rout){//设置采集的目标设备
this.rout = rout;

if(this.needAppend!=null){
this.needAppend.clear();
}else{
this.needAppend = new HashMap<String,StringBuffer>();
}
} public void run(){
String cmd = getTheLogCommandOfRout();
String cmdValue=null;
char startFlag = getTheStatementStartFlag();

if(cmd!=null){

cmdValue =TelnetHelper.getTheValueOfCommandExed(rout,cmd);

}else {
return;
}
analyseValue(cmdValue,startFlag);//分析出有哪些内容应该添加

appendToFile();//添加到文件
}

private String getTheLogCommandOfRout(){
int fa =rout.getFactory();
switch(fa){
case 0: return "dis logbuffer";//华为
case 1: return "show log";//思科
}

return null;
}

private char getTheStatementStartFlag(){
int fa =rout.getFactory();
switch(fa){
case 0: return '%';//华为
case 1: return '*';//思科
}
return ' ';
}

/**
 * 
 * 解析采集到的log数据
 * 
 * @param cmdValue
 * @param startFlag
 */
private void analyseValue(String cmdValue,char startFlag){
// System.out.println("cmdValue::"+cmdValue);
if(cmdValue==null)return;

Date date = new Date();
Date d  = null;
boolean isAppend=false;
// boolean startRecord=false;
int startIndex=0;
String filename=null;
 String[] strArr =cmdValue.split("\r\n");
 
 int type=0;//规定log是哪种格式。 0-格式为:以 startflag开头(%),时间格式为 MMM d HH:mm:ss yyyy;  1-格式为每句中包含双startflag(即是%%),时间格式为MMM d yyyy HH:mm:ss  
//  ArrayList<String> content = new ArrayList<String>();
 for(int i=0;i<strArr.length;i++){
 if(strArr[i]==null||strArr[i].trim().length()==0){
 continue;
 }
 if(strArr[i].trim().charAt(0)==startFlag){
 
 startIndex = i;
 type=0;
 break;
 }else if(strArr[i].trim().indexOf(startFlag+startFlag)!=-1){
 startIndex = i;
 type=1;
 break;
 }
 
 }
 String[] st = null;
 String temp = null;
 
 
 
 

 
 
 for(int i=strArr.length-1;i>=startIndex;i--){//判断是否有需要添加到log日志中的
 if(strArr[i]!=null&&strArr[i].trim().length()<=0)continue;
 
 if(strArr[i].trim().charAt(0)==startFlag){//如果采集的日志数据包含了startFlag
 if(rout.getFactory()==0){
 st =strArr[i].trim().split(" "+(date.getYear()+1900)+" ");
 }else if(rout.getFactory()==1){
 st =strArr[i].trim().split(": %");
 }
 
 if(st==null||st.length<=0)return; 
 temp = st[0].trim();
 temp = temp.substring(1);//去掉startFlag
 if(rout.getFactory()==0){
 d = DateUtil.getDateFromFormatString(temp, "MMM d HH:mm:ss", "en");
 }else if(rout.getFactory()==1){
 d = DateUtil.getDateFromFormatString(temp, "MMM  d HH:mm:ss.SSS", "en");
 }

 filename =getFileName(d);

 if(this.fileName==null||!this.fileName.equals(filename)){//如果刚开始解析或不存在这个log文件

 this.fileContent = getFileContent(filename);
 setFileName(filename);
 if(needAppend.get(filename)==null){//如果 文件名与应追加内容 映射map中 不存在该文件名,则新建映射
 needAppend.put(filename, new StringBuffer());
 }
 }
 
//  System.out.println("fileContent:::"+fileContent);
//  System.out.println(" this.fileContent.indexOf(strArr[i].trim()):::"+ this.fileContent.indexOf(strArr[i].trim()));

 if(this.fileContent!=null&&this.fileContent.indexOf(strArr[i].trim())!=-1){
 isAppend = false;
 continue;//如果已经存在该语句,则不追加
 }
 
 this.needAppend.get(filename).append(strArr[i].trim());
 this.needAppend.get(filename).append("\r\n");
//  this.fileContent=this.fileContent+strArr[i].trim()+"\r\n";
 
 isAppend = true;
 
 }else{//如果该句中不带有 时间标志,则追加到上次时间中
 
 
 if(this.fileName==null){//则说明刚开始解析该logbuffer,而且是logbuffer中无用的信息,则省略掉
 continue; 
 }else{//说明是logbuffer 中有用的信息,但并不以时间标志开始,则将其追加到上次时间标志对应的文件
 //因为log的规律是首先出现日期,再出现log内容
 this.fileContent = getFileContent(this.fileName);
 if(needAppend.get(this.fileName)==null){//如果 文件名与应追加内容 映射map中 不存在该文件名,则新建映射
 needAppend.put(this.fileName, new StringBuffer());
 }
 
if(isAppend){//如果上个带有时间标志的追加了,则追加  this.needAppend.get(this.fileName).append(strArr[i].trim());
 this.needAppend.get(this.fileName).append("\r\n");
//  this.fileContent=this.fileContent+strArr[i].trim()+"\r\n";
}
 
 
 }
 
 }
 
 
 }
 
 strArr = null;
 cmdValue = null;
 this.fileName = null;
 this.fileContent  = null;
}


/**
 * 
 * 更新syslog文件的内容
 * 
 */
private void appendToFile(){
Set<String> names =this.needAppend.keySet();
for(String name:names){
// System.out.println("name append::"+needAppend.get(name).toString());
FileUtil.appendFileContent(name, needAppend.get(name).toString());
}

this.needAppend.clear();

this.needAppend = null;
}

/**
 * 
 * 返回文件名称
 * 
 * @param date
 * @return
 */
private String getFileName(Date date){
String path =PropertiesHandle.getResuouceInfo("SysLogDir");
String deviceName = rout.getRoutName();
path = path+deviceName+System.getProperty("file.separator");
FileUtil.createFolder(path);
String timeStr =DateUtil.getTimeStrInFormat(date, "MM月");
String fileName = path+"log-"+deviceName+"-"+timeStr+".log";
return fileName;
}
/**
 * @param file
 * @return
 */
private String getFileContent(String file){

if(file!=null&&this.fileName!=null&&file.equals(this.fileName))return this.fileContent;

StringBuffer sb = new StringBuffer("");
FileReader fr = null;
try {
 fr = new FileReader(file);

int ch =fr.read();
while(ch!=-1){
sb.append((char)ch);
ch = fr.read();
}

fr.close();
fr = null;
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
return sb.toString();
// e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}finally{
if(fr!=null){
try {
fr.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
fr = null;
}
}

return sb.toString();
} public String getFileName() {
return fileName;
} public void setFileName(String fileName) {

this.fileName = fileName;
}

}
大家帮我看看是什么原因造成CPU占用率过高的,在下在此谢过了