2010-08-17 108 views
56

我正試圖在給定文件夾中搜索給定類型(例如.pdf)的所有文件,並將它們複製到新文件夾中。我需要做的是指定一個根文件夾,並搜索該文件夾及其所有子文件夾中的任何與給定類型(.pdf)相匹配的文件。任何人都可以給我一個關於如何搜索根文件夾的子文件夾及其子文件夾等的手。這聽起來像一個遞歸的方法會在這裏做的伎倆,但我不能正確實施一個? (順便說一句,我正在用ruby實現這個程序)。在某個文件夾及其所有子文件夾中搜索特定類型的文件

回答

54

您需要Find模塊。 Find.find需要一個包含路徑的字符串,並將父路徑以及每個文件和子目錄的路徑傳遞給一個伴隨塊。一些示例代碼:

require 'find' 

pdf_file_paths = [] 
Find.find('path/to/search') do |path| 
    pdf_file_paths << path if path =~ /.*\.pdf$/ 
end 

這將遞歸搜索的路徑,並存儲在數組中以.pdf結尾的文件名。

79

試試這個:

Dir.glob("#{folder}/**/*.pdf") 

這是一樣的

Dir["#{folder}/**/*.pdf"] 

當文件夾變量是路徑要通過搜索的根文件夾。

+0

方法是正確的,但執行是錯誤的。它需要是Dir.glob('**/*。pdf') – jergason 2010-08-17 17:40:25

+2

我認爲OP想要遞歸,不是嗎? – rogerdpack 2012-07-19 19:43:55

+0

最初的回答(rogerdpack)爲我工作,但Jergason's沒有,我害怕。 – Joyce 2013-03-07 23:00:11

9

作爲一個小的改進上面Jergason和馬特的答案,這裏是你如何能凝結成單行:

pdf_file_paths = Find.find('path/to/search').select { |p| /.*\.pdf$/ =~ p } 

它使用查找方法同上,但利用的事實,結果是一個枚舉(並且因此我們可以使用select)來獲得與該組匹配的陣列

16

如果速度是問題,則優選Dir.glob而不是Find.find

Warming up -------------------------------------- 
      Find.find 124.000 i/100ms 
      Dir.glob 515.000 i/100ms 
Calculating ------------------------------------- 
      Find.find  1.242k (± 4.7%) i/s -  6.200k in 5.001398s 
      Dir.glob  5.249k (± 4.5%) i/s -  26.265k in 5.014632s 

Comparison: 
      Dir.glob:  5248.5 i/s 
      Find.find:  1242.4 i/s - 4.22x slower 

 

require 'find' 
require 'benchmark/ips' 

dir = '.' 

Benchmark.ips do |x| 
    x.report 'Find.find' do 
    Find.find(dir).select { |f| f =~ /\*\.pdf/ } 
    end 

    x.report 'Dir.glob' do 
    Dir.glob("#{dir}/**/*\.pdf") 
    end 

    x.compare! 
end 

使用ruby 2.2.2p95 (2015-04-13 revision 50295) [x86_64-darwin15]

+2

謝謝你的帖子。對於像我這樣的初學者來說,找出在Dir.glob和Find.find之間應該使用哪種方法是非常有用的。 – itsh 2016-09-14 18:15:19

+2

在這種情況下查找速度應該比較慢,因爲您使用的是正則表達式。另一方面,Dir.glob並不像正則表達式那樣強大,所以我期望它更快。 – hirowatari 2017-08-18 20:39:51

相關問題