『壹』 用c語言如何操作日誌
日誌就是文件
你直接用stdio.h操作文件就可以了
『貳』 求教編寫一個C語言日誌庫
#include<stdio.h> void main(void) { float a[20]; int i,j; float temp; for(i=0;i<20;i++) { scanf("%f",&a[i]); } for(i=0;i<20;i++) { for(j=i+1;j<20;j++) { if (a[i]>a[j]) { temp=a[i]; a[i]=a[j]; a[j]=temp; } } } printf("從小到大的順序為:\n"); for(i=0;i<20;i++) { printf("%f",a[i]); } putchar('\n'); }
『叄』 LINUX下C語言編程怎麼列印日誌
我們的程序一般都會產生輸出信息。但是伺服器程序一般卻不希望輸出信息到屏幕上,因為沒有人盯著你的程序執行。所以我們要把一些信息寫成日誌文件,正常情況下運行程序的人不用關心日誌里的內容,只有在出現問題的時候才會查看日誌文件里的內容以確定問題所在。
但如果我們的程序要自己生成一個文件來保存日誌卻不是好主意,因為這一方面增加了維護程序運行的人的負擔,另一方面自己維護起系統來也多有不便。
在Linux系統中有一個系統日誌,通常放在/var/log目錄下,比如文件名是syslog的,系統中的一些程序產生的日誌信息都會存放到這個文件里。日誌文件有固定的格式,比如第1列是消息產生的時間,第2列是機器名(因為日誌記錄程序支持遠程連接),第3列是標記信息(一般就是程序名稱)等。而且對應的有一些工具來對這個日誌進行維護,比如通過輪回機制保證日誌文件大小不會把磁碟空間占盡。所以我們把自己程序的信息也寫到這個系統日誌里是比較好的想法。
在GNU C語言庫提供的內容中,有介面可以用來做這件事。用下面的命令查看:
nm -D /lib/libc.so.6 | grep log
可以看到一些調用:
000b9410Tcloselog
0008b870Tgetlogin
0008b960Tgetlogin_r
000d0180T__getlogin_r_chk
000bd190Tklogctl
00027450T__open_catalog
000b9380Topenlog
0008bae0Tsetlogin
000b8b80Tsetlogmask
000b9350Tsyslog
000b9320T__syslog_chk
000b92f0Tvsyslog
000b8da0T__vsyslog_chk
這裡面的三個函數openlog, syslog, closelog是一套系統日誌寫入介面。另外那個vsyslog和syslog功能一樣,只是參數格式不同。
程序的用法示例代碼如下:
#include<syslog.h>
intmain(intargc,char**argv)
{
openlog("MyMsgMARK",LOG_CONS|LOG_PID,0);
syslog(LOG_DEBUG,
"'%s' ",
argv[0]);
closelog();
return0;
}
編譯生成可執行程序後,運行一次程序將向/var/log/syslog文件添加一行信息如下:
Feb1208:48:38localhostMyMsgMARK[7085]:'./a.out'
Feb 12 08:48:38 localhost MyMsgMARK[7085]: This is a syslog test message generated by program './a.out'
LOG_CONS
.
LOG_NDELAY
Opentheconnectionimmediately(normally,).
LOG_NOWAIT
Don』.(TheGNUClibrarydoesnotcreatea
childprocess,.)
LOG_ODELAY
TheconverseofLOG_NDELAY;()iscalled.(Thisisthedefault,andneed
notbespecified.)
LOG_PERROR
(NotinSUSv3.)Printtostderraswell.
LOG_PID
IncludePIDwitheachmessage.
第三個參數指明記錄日誌的程序的類型。
syslog函數及參數
syslog函數用於把日誌消息發給系統程序syslogd去記錄,此函數原型是:
void syslog(int priority, const char *format, ...);
第一個參數是消息的緊急級別,第二個參數是消息的格式,之後是格式對應的參數。就是printf函數一樣使用。
如果我們的程序要使用系統日誌功能,只需要在程序啟動時使用openlog函數來連接syslogd程序,後面隨時用syslog函數寫日誌就行了。
另外,作為syslog的替代程序的新一代工具是syslog-ng,syslog-ng具有很強的網路功能,可以方便地把多台機器上的日誌保存到一台中心日誌伺服器上。
『肆』 c++log4cxx日誌的詳解
一、log4cxx命名規則
Logger由一個String類的名字識別,logger的名字是大小寫敏感的,且名字之間具有繼承的關系,子名有父名作為前綴,用點號.分隔。如:x.y是x.y.z的父親。根logger (root logger)是所有logger的祖先, 它具有如下屬性:1) 它總是存在的;2) 它不可以通過名字獲得。通過調用public static Logger Logger.getRootLogger()獲得root logger;通過調用public static Logger Logger.getLogger(String name)或者public static Logger Logger.getLogger(Class clazz)獲得或者創建)一個named logger。後者相當於調用Logger.getLogger(clazz.getName())。在某對象中,用該對象所屬的類為參數,調用Logger.getLogger(Class clazz)以獲得logger被認為是目前 所知的最理智的命名logger的方法。
二、log4cxx Log Level級別介紹
每個logger都被分配了一個日誌級別 (log level),用來控制日誌信息的輸出。未被分配level的 logger將繼承它最近的.父logger的level。每條輸出到logger的日誌請求(logging request)也都有一個 level,如果該request的level大於等於該logger的level,則該request將被處理(稱為enabled);否則該 request將被忽略。故可得知:1、logger的level越低,表示該logger越詳細 2、logging request的 level越高,表示該logging request越優先輸出 3、如果沒有設置日誌記錄器(Logger)的級別,那麼它將 會繼承最近的祖先的級別。因此,如果在包com.foo.bar中創建一個日誌記錄器(Logger)並且沒有設置級 別,那它將會繼承在包com.foo中創建的日誌記錄器(Logger)的級別。如果在com.foo中沒有創建日誌記錄 器(Logger)的話,那麼在com.foo.bar中創建的日誌記錄器(Logger)將繼承root 日誌記錄器(Logger) 的級別,root日誌記錄器(Logger)經常被實例化而可用,它的級別為DEBUG。
Level類中預定義了五個level,它們的大小關系如下:Level.ALL < Level.DEBUG < Level.INFO < Level.WARN < Level.ERROR < Level.FATAL < Level.OFF
三、log4cxx(log4j) Log layout介紹
org.apache.log4j.HTMLLayout(以HTML表格形式布局),
org.apache.log4j.PatternLayout(可以靈活地指定布局模式),
org.apache.log4j.SimpleLayout(包含日誌信息的級別和信息字元串),
org.apache.log4j.TTCCLayout(包含日誌產生的時間、線程、類別等等信息)
四、log4cxx Log 格式化信息介紹
Log4J採用類似C語言中的printf函數的列印格式格式化日誌信息,列印參數如下:
%m 輸出代碼中指定的消息
%p 輸出優先順序,即DEBUG,INFO,WARN,ERROR,FATAL
%r 輸出自應用啟動到輸出該log信息耗費的毫秒數
%c 輸出所屬的類目,通常就是所在類的全名
%t 輸出產生該日誌事件的線程名
%n 輸出一個回車換行符,Windows平台為「rn」,Unix平台為「n」
%d 輸出日誌時間點的日期或時間,默認格式為ISO8601,也可以在其後指定格式,比如:%d{yyyy MMM dd
HH:mm:ss,SSS},輸出類似:2002年10月18日 22:10:28,921 %l 輸出日誌事件的發生位置,包括類目名
、發生的線程,以及在代碼中的行數。
五、log4cxx Log appender種類介紹
Log4cXX提供的appender種類:
org.apache.log4j.ConsoleAppender 控制台
org.apache.log4j.DailyRollingFileAppender 每天產生一個日誌文件
org.apache.log4j.FileAppender 文件org.apache.log4j.RollingFileAppender 文件大小達到指定尺寸的
時候產生一個新的文件
六、log4cxx Log Filter介紹
包括選擇過濾器和設置過濾條件,可選擇的過濾器包括:LogLevelMatchFilter、LogLevelRangeFilter、和 StringMatchFilter:
1、對LogLevelMatchFilter來說,過濾條件包括LogLevelToMatch和AcceptOnMatch(true|false),只有 當log信息的LogLevel值與LogLevelToMatch相同,且AcceptOnMatch為true時才會匹配。
2、對LogLevelRangeFilter來說,過濾條件包括LogLevelMin、LogLevelMax和AcceptOnMatch,只有當log信 息的LogLevel在LogLevelMin、LogLevelMax之間同時AcceptOnMatch為true時才會匹配。
3、對StringMatchFilter來說,過濾條件包括StringToMatch和AcceptOnMatch,只有當log信息的LogLevel 值與StringToMatch對應的LogLevel值與相同,且AcceptOnMatch為true時會匹配。
七、log4cxx additivity屬性介紹
它是 子Logger 是否繼承 父Logger 的 輸出源(appender)的標志位。具體說,默認情況下子Logger會繼承父Logger的appender,也就是說子Logger會在父Logger的appender里輸 出。若是additivity設為false,則子Logger只會在自己的appender里輸出,而不會在父Logger的appender里輸 出。
『伍』 LINUX下C語言編程怎麼列印日誌
將日誌寫到文件中去,在到文件中去看日誌
例如:
int
mig_log(fmt,va_alist)
char
*fmt
;
va_dcl
{
va_list
ap
;
FILE
*fp
;
char
log_file[81]
;
struct
tm
*p_tm
;
time_t
clock
;
ap=(char
*)&va_alist
;
time(&clock)
;
p_tm=localtime(&clock)
;
sprintf(log_file,"%s/mig_%4d%.2d%.2d.log",
getenv("HOME"),
p_tm->tm_year+1900,
p_tm->tm_mon+1,
p_tm->tm_mday)
;
fp=fopen(log_file,"at")
;
if(fp==(FILE
*)0)
{
fprintf(stderr,"mig_err_log():can't
open
the
file
%s
!\n",log_file);
return
;
}
fprintf(fp,"%.2d/%.2d/%4d
%.2d:%.2d:%.2d
",
p_tm->tm_mon+1,\
p_tm->tm_mday,\
p_tm->tm_year+1900,\
p_tm->tm_hour,\
p_tm->tm_min,\
p_tm->tm_sec)
;
vfprintf(fp,fmt,ap)
;
fclose(fp)
;
}
這個就是寫日誌的函數
你這樣調用:mig_log("日誌開始[%s]->[%d]\n",__FILE__,__LINE__)
;
mig_log("日誌開始!\n")都可以的
『陸』 C語言怎麼封裝自己寫的函數
用C語言的時候,您是否還在使用printf函數來輸出日誌呢?您是否考慮過將printf函數列印的內容存到文件中去呢?您是否想擁有一個可選擇的既支持輸出到屏幕又支持存儲到文件中的日誌函數呢?很高興的告訴您,如果您願意的話,歡迎使用本人編寫的一個一套日誌函數,該套函數由五部分組成,分別是宏變數BUF_SIZE、結構體log_st、log_init函數、log_debug函數和log_checksize函數。其中宏變數BUF_SIZE用來限制每次輸出的日誌的最大長度;結構體用來存儲用戶需求,包括文件路徑、文件描述符號、單個文件最大大小、輸出方式標志、文件命名標志等;log_init函數用來完成用戶需求錄入、文件創建等功能,在mian函數的開始調用一次即可;log_debug函數的功能跟printf很類似,是在printf基礎上進行的擴充,實現將日誌輸出到屏幕或者寫入到文件,在需要列印日誌的地方調用該函數;log_checksize函數用來檢測日誌文件大小是否超過最大大小限制,它需要您定時或者定點調用它,如果一直不調用,則日誌文件將不受指定的最大大小限制。
一、定義宏變數BUF_SIZE
view plain to clipboardprint?
#defineBUF_SIZE1024
二、定義log_st結構體
view plain to clipboardprint?
typedefstruct_log_stlog_st;
struct_log_st
{
charpath[128];
intfd;
intsize;
intlevel;
intnum;
};
三、定義log_init函數
參數說明:path——您要存儲的文件路徑;size——單個文件的最大大小,如果超過該大小則新建新的文件用來存儲;level——日誌輸出方式,建議在上層限制其值的范圍為0到3,0表示日誌既不輸出到屏幕也不創建文件和保存到文件,1表示日誌保存到文件但不輸出到屏幕,2表示日誌既輸出到屏幕也保存到文件,3表示日誌只輸出到文件而不創建文件和存入文件;num——日誌文件命名方式,非0表示以(int)time(NULL)作為文件名來保存文件,文件數量隨著日誌量的遞增而遞增;0表示以「.new」和「.bak」為文件名來保存文件,文件數量不超過兩個,隨著日誌量的遞增,舊的日誌文件將被新的覆蓋,更直觀的說就是說.new」和「.bak」文件只保存最近的日誌。
view plain to clipboardprint?
log_st*log_init(char*path,intsize,intlevel,intnum)
{
charnew_path[128]={0};
if(NULL==path||0==level)returnNULL;
log_st*log=(log_st*)malloc(sizeof(log_st));
memset(log,0,sizeof(log_st));
if(level!=3)
{
//thenumusetocontrolfilenaming
log->num=num;
if(num)
snprintf(new_path,128,"%s%d",path,(int)time(NULL));
else
snprintf(new_path,128,"%s.new",path);
if(-1==(log->fd=open(new_path,O_RDWR|O_APPEND|O_CREAT|O_SYNC,S_IRUSR|S_IWUSR|S_IROTH)))
{
free(log);
log=NULL;
returnNULL;
}
}
strncpy(log->path,path,128);
log->size=(size>0?size:0);
log->level=(level>0?level:0);
returnlog;
}
四、定義log_debug函數
view plain to clipboardprint?
voidlog_debug(log_st*log,constchar*msg,...)
{
va_listap;
time_tnow;
char*pos;
char_n=' ';
charmessage[BUF_SIZE]={0};
intnMessageLen=0;
intsz;
if(NULL==log||0==log->level)return;
now=time(NULL);
pos=ctime(&now);
sz=strlen(pos);
pos[sz-1]=']';
snprintf(message,BUF_SIZE,"[%s",pos);
for(pos=message;*pos;pos++);
sz=pos-message;
va_start(ap,msg);
nMessageLen=vsnprintf(pos,BUF_SIZE-sz,msg,ap);
va_end(ap);
if(nMessageLen<=0)return;
if(3==log->level)
{
printf("%s ",message);
return;
}
if(2==log->level)
printf("%s ",message);
write(log->fd,message,strlen(message));
write(log->fd,&_n,1);
fsync(log->fd);
}
五、定義log_checksize函數
view plain to clipboardprint?
voidlog_checksize(log_st*log)
{
structstatstat_buf;
charnew_path[128]={0};
charbak_path[128]={0};
if(NULL==log||3==log->level||'