2023年政策修订增补工作正在进行中,欢迎参与!
  • Moegirl.ICU:萌娘百科流亡社群 581077156(QQ),欢迎对萌娘百科运营感到失望的编辑者加入
  • Moegirl.ICU:账号认领正在试运行,有意者请参照账号认领流程

說明:濫用過濾器使用指導/條件

萌娘百科,萬物皆可萌的百科全書!轉載請標註來源頁面的網頁連結,並聲明引自萌娘百科。內容不可商用。
跳至導覽 跳至搜尋
Commons-emblem-notice.svg
這個頁面「Help:濫用過濾器使用指導/條件」是萌娘百科的幫助文檔
  • 本文用於介紹萌娘百科中一些特定功能的操作方法;
  • 本文僅是一篇論述,不屬於方針或指引。如果本指南與相關方針或指引發生衝突或存在不一致的情況,請以方針或指引的條文為準。

論述: 條件判斷限制器是一種避免性能問題的特設工具。從某些程度上說,如果閣下非常關心性能問題,執行時間一般是一個極好的參考性能指標。每過濾器執行時間和條件判斷數量有些時候並不準確(競態條件可以導致它們出現了偏差),但是總體上來說它們也可以用作參考指標。

條件判斷限制是一種比較運算符數量和函數(方法)調用數量的跟蹤機制。然而它也可以在不影響結果的情形下機智地跳過函數(方法)和括號組。舉個例子,在表達式 A & B 中,B 的情況只會在 A 為真時被評估。出於此理由,將簡單的條件(例如檢查文章命名空間)放在複雜的表達式前對性能是大有脾益的。最後需要注意的是,函數(方法)將會被緩存,所以它們只會在第一次被調用的時候增加條件判斷計數。


MediaWiki 1.27 之前

介於萌百的實際部署情況,此段不翻譯,請參考 to MediaWiki 1.27 Prior to MediaWiki 1.27 上的內容。

MediaWiki 1.27 和更新版本

實用建議

  • 將容易評估但是難匹配條件的項目放在過濾器前面。這樣可以使得過濾器更快完成,且可以改善運行時間,減少條件判斷用量。
  • 在文本里檢測多段文字的出現次數時(通常用於檢測垃圾信息),使用 contains_any(text, 'a', 'b', 'c')text rlike 'a|b|c' 遠快於 對每個字符串進行單獨的測試 ('a' in text | 'b' in text | 'c' in text)。這樣也使用了更少的條件判斷。
  • 所有除了 user_nameuser_* 變量可能需要一次數據庫查詢。因此,使用它們相比使用預定義變量如 action and article_namespace 來說成本更為昂貴。它們應該不被作為過濾器的第一個條件使用(取決於新的順序使得匹配的完成的耗時,這可能會減少或增加條件判斷計數,但應該改善了總體性能)。


常規計數

條件判斷計數
Rules 使用的條件 備註
'foo' == 'bar' 1 一個計數為一次的簡單條件判斷。
'foo' == 'bar' | 'baz' == 'qaz' 2
'foo' == 'bar' & 'baz' == 'bar' 1 不需要被評估來用於決定最終結果的測試沒有被計數。 (短路求值)
  • 在第一個例子中, 'foo' == 'bar' 為假, 所以第二個測試對最終結果沒有影響(結果均為假)。
  • 在第二個例子中, 'foo' == 'foo' 為真, 所以第二個測試對最終結果沒有影響(結果均為真)。
'foo' == 'foo' | 'baz' == 'qaz' 1
str_replace( 'FooFoo', 'Foo', '' ) == 'bar' 2 每個函數(方法)調用被視作一次條件判斷計數。
str_replace( 'FooFoo', 'Foo', '' ) == 'bar'
| str_replace( 'FooFoo', 'Foo', '' ) == 'baz'
3 相同參數的同函數(方法)調用被視作僅一次條件判斷計數。

例子1

舉一個實際例子,考慮 英文維基百科的過濾器 #59:

article_namespace == 6
& !("autoconfirmed" in user_groups)
& !(user_name in article_recent_contributors)
& rcount ("\{\{.*\}\}", removed_lines) > rcount ("\{\{.*\}\}", added_lines)

這可以被簡化為:

A & !B & !C & fun1() > fun2()

取決於變量的值,過濾器可以消耗1到6個條件判斷:

  • 1 個條件判斷 (1 次比較) 如果第一個測試的值為假:剩下的測試將不會被評估
  • 2 個條件判斷 (2 次比較) 如果第一個測試的值為真, 但第二個測試的值為假:剩下的測試將不會被評估
  • 3 個條件判斷 (3 次比較) 如果第一個和第二個測試的值為真,但第三個測試的值為假:剩下的測試將不會被評估
  • 6 個條件判斷 (3 次比較 + 2 次函數(方法)調用 + 1 次比較) 如果第一個、第二個和第三個測試的值為真

如果初始條件罕見地為真(比如 article_namespace == 6 可能是),那麼過濾器在多數情況只需要下消耗一個條件判斷。