簡體   English   中英

PHP中的file_exist()是一個非常昂貴的操作嗎?

[英]Is file_exist() in PHP a very expensive operation?

我正在為我正在設計的論壇引擎添加頭像,我在辯論是否要做一些簡單的事情(論壇圖片命名為.png)並使用PHP在顯示之前檢查文件是否存在,或者做一些事情有點復雜(但不多)並使用數據庫字段來包含要顯示的圖像的名稱。

我更願意親自使用file_exists()方法,因為如果當前的那個(默認)還沒有存在,那么我可以輕松地回歸到“默認”虛擬形象,並且它很容易實現代碼。 但是,我擔心性能,因為每個用戶在論壇閱讀頁面上每頁面顯示一次就會運行一次。 所以我想知道,PHP中的file_exists()函數會導致在高流量條件下導致顯着性能下降的任何重大減速嗎?

如果不是,那很好。 如果是這樣,您對跟蹤用戶上傳圖像的替代方案有何看法? 謝謝!

PS:我可以看到的代碼差異是文件檢查版本允許文件進行通話,而數據庫表單信任數據庫是准確的並且不打算檢查。 (它只是一個傳遞給瀏覽器的URL。)

與其他海報所說的一樣,file_exists()的結果由PHP自動緩存以提高性能。

但是,如果您已經從數據庫中讀取用戶信息,那么您也可以將信息存儲在那里。 如果用戶只允許使用一個頭像,則可以在“has avatar”(1/0)的列中存儲單個位,然后使用與用戶ID相同的文件名,並使用SELECT CONCAT(IF(has_avatar, id, 'default'), '.png') AS avatar FROM users

您還可以考慮將實際圖像作為BLOB存儲在數據庫中。 將它放在自己的表中,而不是將其作為列附加到用戶表。 這樣做的好處是它使您的論壇非常容易備份 - 您只需導出數據庫。

由於您的Web服務器在顯示您的網頁的過程中已經執行了大量(相當於)file_exists()操作,因此腳本運行的操作可能不會產生可測量的影響。 Web服務器可能至少會:

  • 一個用於Web根目錄的每個子目錄(用於檢查存在性和符號鏈接)
  • 一個用於檢查Web根目錄的每個子目錄的.htaccess文件
  • 一個是因為你的腳本存在

這並沒有考慮PHP可能會做的更多。

在實際的性能測試中,您將發現file_exists非常快。 實際上,在php中,當同一個url是“stat”'d兩次時,第二個調用就是從php的內部stat緩存中提取的。

這只是在php運行范圍內。 即使在運行之間,文件系統/ os也會傾向於將文件積極地放入文件系統緩存中,如果文件足夠小,不僅文件存在測試直接從內存中出來,而且整個文件也是如此。

這里有一些支持我理論的真實數據:

我剛剛對linux命令行實用程序“find”和“xargs”進行了一些性能測試。 在收益中,我在13000個文件上執行了一個文件存在測試,每次100次,在30秒內,這樣每秒平均43,000次靜態測試,所以肯定,如果你比較它的時候它的速度很慢它采用了8分9,但在真實的場景中,你將需要這樣一個可怕的很多次看到一個顯着的性能問題。

如果你有43000 用戶同時訪問你的頁面,在一秒鍾的時間內,我認為你將有更大的顧慮,而不是復制文件存在的狀態或多或少的時間。平均情況下的內存。

至少在PHP4中,我發現調用file_exists肯定會殺死我們的應用程序 - 它在庫中非常重復,因此我們必須使用分析器來查找它。 刪除呼叫增加了一些頁面的計算十幾次(呼叫是重復的)。

它可能在PHP5中緩存file_exists,但至少在PHP4中並非如此。

現在,如果你不在循環中,很明顯,file_exists不會是一個大問題。

file_exists()本身並不慢。 真正的問題是如何配置系統以及性能瓶頸在哪里。 請記住,數據庫也必須將內容存儲在磁盤上,因此無論哪種方式,您都可能面臨磁盤活動。 另一方面,數據庫和文件系統通常都采用某種形式的透明緩存來優化重復訪問。

你可以很容易地采取任何一種方式,因為你的性能瓶頸可能會出現在其他地方。 我可以看到它是一個顯而易見的選擇的唯一地方是,如果你在某種超級共享主機上有大量的磁盤爭用,但可能數據庫訪問是在一個單獨的集群上更快(反之亦然)。

在過去,我已將圖像元數據存儲在數據庫中(包括其名稱),以便我們可以生成有用的統計數據。 更重要的是,存儲圖像數據(不是文件本身,只是元數據)有利於改變 如果您將來需要“批准”圖像,或者想刪除它而不刪除文件,該怎么辦?

根據“默認”頭像...如果找不到該用戶的記錄,只需使用默認值。

無論哪種方式,file_exists()或db,它都不應該成為擔心的瓶頸。 然而,一種解決方案更加可擴展。

如果性能是您唯一的考慮因素,那么file_exists()將比數據庫查找便宜得多。

畢竟這只是使用系統調用的目錄查找。 在第一次執行腳本之后,大多數相關目錄將被緩存在存儲中,因此涉及的實際I / O非常少,並且“file_exists()”是一種常見的操作,它和底層系統調用將是高度的在任何常見的php / os組合上進行優化。

正如約翰二世所說。 如果額外的功能和用戶界面功能是優先考慮的話,那么數據庫就是最佳選擇。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM