基於ACE實現C 目錄遍歷

2021-04-02 23:56:51 字數 2654 閱讀 4070

目錄遍歷,在軟體程式設計中屬於常見的需求;如:病毒掃瞄、源**編輯、檔案比較。在

windows

環境,使用

findfirstfileex

、findnextfile

(詳細情況可以參考

msdn

)等檔案訪問函式,能夠實現目錄遍歷;在

posix

環境,可以使用

open_dir

。跨平台不是這裡討論的重點。

ace提供的

opendir_emulation

、readdir_emulation

函式族與

windows

的findfirstfileex

、findnextfile

功能是一致的;其本意也是提供一種類似介面的跨平台封裝。但是,直到版本

4.361

都還是沒有加入其它平台的處理;現在只能認為

ace把一些記憶體管理包裝到自己的函式族中了。

以下的討論也基於如上的函式實現。

目錄的組織可以分成

3種情況:

1)下面也是目錄;

2)下面是檔案;3)『

.』和『..』

其中『.

』和『..

』比較特殊,需要過濾。基於上述分析,函式遞迴呼叫的演算法比較簡單。為**如下:

開啟目錄;

如果是檔案,呼叫檔案處理函式;

如果是目錄:

如果目錄名是『

.』或者『

..』,繼續;

對目錄下所有內容:

呼叫本函式;

讀取目錄;

清除處理

本文討論的是:如何基於

oo的實現。明顯的,如上的遞迴演算法可以封裝到乙個類中,這是不變的地方;變化的是對檔案的處理,比如:列印,掃瞄等。檢查演算法,檔案處理,可以用虛函式,實現

hook

處理,可以通過過載此函式實現功能拓展。另外,容易考慮到的內容是,檔案過濾,如對

*.exe

或者*.cpp

進行某種操作。

有了如上的分析,容易得到如下的類定義:

class

dirvisitor

}

else

//recursive call

while(dir)

ace_os::closedir_emulation(base_dir);

}}

protected:

virtual

int handle_one_file(const string& path_name, const string& dir_name)

virtual

bool comparer(const string& name, const string& key)

return

false;

}

virtual

bool bypass(const string& name)

};

類的對外藉口只有乙個

open_one_dir

,其他的都被封裝起來;可以拓展的是

3個保護函式:

1)handle_one_file:

提供一種預設處理,列印到標準輸出;

2)comparer:

檔名比較方法,預設是字串包含與否的比較;可以拓展為模糊比較;

3)bypass

:忽略檔案的條件;這裡預設不忽略。

這樣客戶端**就簡單了:

intmain(int argc, char** argv)

dirvisitor visitor;

visitor.get_one_dir(string(argv[1]), string(""));

}

這樣的**能夠顯示乙個目下的所有目錄和檔案。如ace/doc目錄的掃瞄結果:

要進行過濾,只要過載

bypass

,這裡提供一種對

c++檔案顯示的範例:

bool

cplusvisitor::bypass(const string& name)

if(comparer(name, string(".c")))

if(comparer(name, string(".c")))

if(comparer(name, string(".cpp")))

if(comparer(name, string(".i")))

if

(comparer(name, string(".inl")))

return

true;

}

關於

handle_one_file

方法:引數1,

path_name

提供了帶路徑的檔名;引數2,

key提供不帶路徑的檔名,方便處理。

小結:這裡提供的基於

ace的目錄遍歷,由於其

oo的封裝,方便實用;使用

ace的目的就是利用其跨平台的包裝。為了目錄遍歷的跨平台性,可以自己封裝

posix

的opendir_emulation

、readdir_emulation

函式族,也可以等待

ace提供

^---^。

基於委託機制的(目錄)檔案遍歷

這個示例程式基本實現了dir命令的行為,但是是使用了objectivec的委託機制,思想是不錯的,共享之 以後需要用到可以直接拿來用,因為委託機制真的很不錯 檔名 enumfile.h 工程名 enumfile 作 者 ccnyou ifndef enumfile h define enumfile...

遍歷目錄的非遞迴實現

在遞迴計算目錄數目,檔案數目,目錄大小等功能中,我們常用的方式是使用遞迴來實現。但是,遞迴實現因為會不斷向呼叫堆疊中存入資料 包括當前執行的狀態變數等資料 實際上會大量占用記憶體空間,同時執行時間也會受到影響。我們通過乙個儲存目錄路徑的佇列,可以很優雅地實現非遞迴的目錄遍歷,下面我們通過遞迴統計目錄...

linux 遞迴遍歷目錄的實現

假就直接列印 printf s t ld n name,sb.st size return void read dir char dir while sdp readdir dp 讀這個目錄項,繼續判斷是不是目錄,如果是目錄iu還得再進入,如果是檔案就列印 iffile sdp d name 不能直...