巧妙的利用C 的特性實現Profiling

2021-04-01 03:00:25 字數 1589 閱讀 6255

軟體中profile的解釋很多,有時候指的是一組設定值,這裡說的profile是對執行程式的資料取樣,獲得記憶體使用和執行時間的紀錄,通過分析得以優化**。

1)記憶體profile。c++提供巨集和函式過載的功能,由此可以新增對記憶體的紀錄,將一下**放在標頭檔案中,專案中每個.cpp檔案都include這個標頭檔案,使其產生效應。

#ifdef _debug
#define new((x)) newobj((__function__, __line__, (x));
#define delete((x)) deleteobj(__function__, __line__, (x));
inline void * newobj(const char * function, int line, size_t size)
inline void deleteobj(const char * function, int line, void *ptr)
#endif

至於如何紀錄新增釋放記憶體,方法很多,可以直接列印出來或者寫到乙個檔案,不過這樣非常影響效率,而且不利於產生容易閱讀的輸出。比較合理的方法,建立乙個singletion的類,每次紀錄都通過這個類新增紀錄,這個類的析構函式把所有的紀錄按照需要的方式dump出來。

過載new/delete僅僅用於做profile,在debug版本中發現記憶體分配問題,在release版本中通過不定義_debug去掉。

1)執行時間profile。要獲得某一段**的執行時間,就得在入口紀錄乙個時間,在出口記錄乙個時間,然後取二者之差,這樣的**比較難看,其實可以利用c++程式對區域性變數的處理。c++程式執行到乙個scope結束的時候會刪除這個scope裡面區域性變數,也就是呼叫其的析構函式

#ifdef _debug

#define profile_begin profile p(__file__, __function__, __line__);

class profile

public:

profile(const char * file, const char *function, int line)

//record info

begintimestamp = ...//current time

~profile()

timegap = current time - begintimestamp;

//register info

private:

int begintimestamp;

int timegap;

#else

#define profile_begin

#endif

這樣在源**裡面,只需要在乙個函式入口寫上profile_begin,就可以獲得這個函式體的執行時間。

int foo()

profile_begin

如果想要獲得函式中某一部分code的執行時間,可以把這一部分用{}擴起來,在開始處加乙個profile_begin.

如果想要獲得函式中某一部分code的執行時間,可以把這一部分用{}擴起來,在開始處加乙個profile_begin.

利用CSS3特性巧妙實現漂亮的DIV箭頭

還有傲遊 的導航條 像傲遊賬戶上方這種箭頭更需要多幅以表現箭頭和hover的效果。實現的原理是 我們可以將箭頭看作是乙個矩形或者菱形的乙個角,使用css3的屬性transform來實現矩形的旋轉。朝上的箭頭需要將矩形旋轉45度,我們使用transform rotate 45deg 來實現,另外針對不...

利用CSS3特性巧妙實現漂亮的DIV箭頭

還有傲遊 的導航條 像傲遊賬戶上方這種箭頭更需要多幅以表現箭頭和hover的效果。實現的原理是 我們可以將箭頭看作是乙個矩形或者菱形的乙個角,使用css3的屬性transform來實現矩形的旋轉。朝上的箭頭需要將矩形旋轉45度,我們使用transform rotate 45deg 來實現,另外針對不...

利用CSS3特性巧妙實現漂亮的DIV箭頭

還有傲遊 的導航條 像傲遊賬戶上方這種箭頭更需要多幅以表現箭頭和hover的效果。實現的原理是 我們可以將箭頭看作是乙個矩形或者菱形的乙個角,使用css3的屬性transform來實現矩形的旋轉。朝上的箭頭需要將矩形旋轉45度,我們使用transform rotate 45deg 來實現,另外針對不...