#zephir-(9)類和對象2#php
##前言## 先在這裏感謝各位zephir開源技術提供者git
zephir全面使用對象編程,這就是爲何拓展的使用方式只能是方法和類,你也將看到,大部分的時間,運行時錯誤引起異常,而不是致命錯誤或警告。今天講一步步講解zephir類方法變量範圍等等的使用,但願你們喜歡.github
注:筆者水平有限,說的不正確的地方但願你們多多指正,一同交流技術編程
附上:安全
喵了個咪的博客:w-blog.cnapp
zephir官網地址:http://zephir-lang.com/函數
github地址:https://github.com/phalcon/zephir優化
##嚴格/靈活的參數的數據類型##this
在ZEPHIR,你能夠指定一個方法的每一個參數的數據類型。缺省狀況下,這些數據類型是靈活的,這意味着,若是使用錯誤的(但兼容)的數據類型的值被傳遞,ZEPHIR將嘗試轉換爲預期的類型:spa
public function filterText(string text, boolean escape=false) { //... }
被調用:
<?php $o->filterText(1111, 1); // OK $o->filterText("some text", null); // OK $o->filterText(null, true); // OK $o->filterText("some text", true); // OK $o->filterText(array(1, 2, 3), true); // 失敗
然而,傳遞一個錯誤的類型可能會常常致使錯誤,不使用特定的API會產生意想不到的效果。您能夠經過設置一個嚴格的數據類型的參數禁止自動轉換:
public function filterText(string! text, boolean escape=false) { //... }
如今,大多數錯誤類型的調用會致使一個異常因爲無效數據類型傳遞:
<?php $o->filterText(1111, 1); // 失敗 $o->filterText("some text", null); // OK $o->filterText(null, true); // 失敗 $o->filterText("some text", true); // OK $o->filterText(array(1, 2, 3), true); // 失敗
經過指定什麼參數嚴格,什麼是靈活的,開發人員能夠作到真正想要的定製行爲。
##只讀參數##
使用關鍵字「const」能夠參數標記爲只讀的,內部參數標註該屬性不能修改方法:
namespace App; class MyClass { // "a" 是一個常量 public function getSomeData(const string a) { // 這將拋出一個編譯器異常 let a = "hello"; } }
當一個參數被聲明爲只讀的時候,編譯器可使安全假設和對這些變量進行進一步的優化。
##類的屬性##
類成員變量被稱爲「屬性」。默認狀況下,他們做爲PHP的屬性。屬性實現一般使用可見性修飾符,在Zephir中可見性修飾符是強制性的:
namespace Test; class MyClass { public myProperty1; protected myProperty2; private myProperty3; }
在類方法訪問非靜態屬性能夠經過使用->(對象操做符):這個->屬性:
namespace Test; class MyClass { protected myProperty; public function setMyProperty(var myProperty) { let this->myProperty = myProperty; } public function getMyProperty() { return this->myProperty; } }
屬性能夠有默認值。這些值必須可以被定義,編譯時,不得依賴於運行時的其餘值:
namespace Test; class MyClass { protected myProperty1 = null; protected myProperty2 = false; protected myProperty3 = 2.0; protected myProperty4 = 5; protected myProperty5 = "my value"; }
##更新屬性##
開發人員能夠經過「->屬性」更新屬性值:
let this->myProperty = 100;
zephir會檢查該屬性是否存在,若是一個屬性沒有聲明,你會獲得一個編譯警告:
CompilerException: Property '_optionsx' is not defined on class 'App\MyClass' in /Users/scott/utils/app/myclass.zep on line 62 this->_optionsx = options; ------------^
若是你想避免這個編譯器驗證或動態建立一個屬性,您可使用字符串的屬性名經過"{}"將屬性名包裹起來:
let this->{"myProperty"} = 100;
您還可使用一個簡單的變量更新屬性,屬性名稱將從變量獲取:
let someProperty = "myProperty"; let this->{someProperty} = 100;
##讀屬性##
屬性能夠經過「->」運算符獲取:
echo this->myProperty;
當更新屬性能夠動態地讀:
//避免編譯器檢查或動態的定義的屬性 echo this->{"myProperty"}; //讀取和使用一個變量名 let someProperty = "myProperty"; echo this->{someProperty}
##類的常量##
類是保持不變的,一旦擴展被編譯的類常量就已經確認下來了。
namespace Test; class MyClass { const MYCONSTANT1 = false; const MYCONSTANT2 = 1.0; }
類常量可使用類名稱和訪問靜態操做符(::):
namespace Test; class MyClass { const MYCONSTANT1 = false; const MYCONSTANT2 = 1.0; public function someMethod() { return MyClass::MYCONSTANT1; } }
##調用方法##
方法能夠被使用在PHP對象操做符(- >)調用:
namespace Test; class MyClass { protected function _someHiddenMethod(a, b) { return a - b; } public function someMethod(c, d) { return this->_someHiddenMethod(c, d); } }
靜態方法必須調用使用靜態操做符(::):
namespace Test; class MyClass { protected static function _someHiddenMethod(a, b) { return a - b; } public static function someMethod(c, d) { return self::_someHiddenMethod(c, d); } }
你能夠以動態的方式調用方法以下:
namespace Test; class MyClass { protected adapter; public function setAdapter(var adapter) { let this->adapter = adapter; } public function someMethod(var methodName) { return this->adapter->{methodName}(); } }
##參數的命名##
ZEPHIR支持名稱或關鍵字參數調用方法的參數。若是你想經過以任意順序參數,記錄參數的含義或以更優雅的方式指定參數命名參數能夠是有用的。
考慮下面的例子,一個名爲「Image」類有接收四個參數的方法:
namespace Test; class Image { public function chop(width = 600, height = 400, x = 0, y = 0) { //... } }
使用標準方法的調用方法:
i->chop(100); // width=100, height=400, x=0, y=0 i->chop(100, 50, 10, 20); // width=100, height=50, x=10, y=20
使用命名參數,您能夠:
i->chop(width: 100); // width=100, height=400, x=0, y=0 i->chop(height: 200); // width=600, height=200, x=0, y=0 i->chop(height: 200, width: 100); // width=100, height=200, x=0, y=0 i->chop(x: 20, y: 30); // width=600, height=400, x=20, y=30
當編譯器在編譯時不知道這些參數的正確順序 他們必須解決在運行時,在這種狀況下,可能會有一個最小附加額外的開銷:
let i = new {someClass}(); i->chop(y:30, x: 20);
##總結##
那麼到這裏關於zephir類方法相關的知識就已經結束了,那麼從下節開始將講解內置的一些方法函數的使用,已經流程控制語句,但願你們喜歡!
應爲確實zephir的類方法這一塊的類容比較多,筆者在這裏分紅兩個小節進行說明,多謝你們的支持!
注:筆者能力有限有說的不對的地方但願你們可以指出,也但願多多交流!
zephir技術交流:246348908 歡迎你們的加入!
感謝zephir開發人員: