日韩无码专区无码一级三级片|91人人爱网站中日韩无码电影|厨房大战丰满熟妇|AV高清无码在线免费观看|另类AV日韩少妇熟女|中文日本大黄一级黄色片|色情在线视频免费|亚洲成人特黄a片|黄片wwwav色图欧美|欧亚乱色一区二区三区

RELATEED CONSULTING
相關(guān)咨詢(xún)
選擇下列產(chǎn)品馬上在線(xiàn)溝通
服務(wù)時(shí)間:8:30-17:00
你可能遇到了下面的問(wèn)題
關(guān)閉右側(cè)工具欄

新聞中心

這里有您想知道的互聯(lián)網(wǎng)營(yíng)銷(xiāo)解決方案
簡(jiǎn)單的this,麻煩的this

 周末的Hello World咖啡館總是熱鬧非凡。 

Java , Python, Ruby, JavaScript圍坐在一起,一邊喝咖啡,一邊海闊天空。   

C老頭兒則待在一旁,冷眼旁觀。 

聊著聊著,這話(huà)題不知怎么著轉(zhuǎn)移到了“this”上來(lái)了。 

Java 說(shuō): “唉!你們不知道吧,對(duì)于一個(gè)初學(xué)Java的人來(lái)說(shuō),this 是非常難于理解的。”  

Python說(shuō):“this 在你那里已經(jīng)夠簡(jiǎn)單了啊。還難于理解?”

“我們都是支持面向?qū)ο缶幊痰?,在我這里,this 可以用到實(shí)例方法或者構(gòu)造器中,表示對(duì)當(dāng)前對(duì)象實(shí)例的引用?!? 

 
 
 
 
  1. public class Point { 
  2.     private double x = 0.0; 
  3.     private double y = 0.0; 
  4.     public Point(int x, int y) { 
  5.         this.x = x; 
  6.         this.y = y; 
  7.     } 
  8.  
  9.    public double distanceTo(Point that) { 
  10.         double dx = this.x - that.x; 
  11.         double dy = this.y - that.y; 
  12.         return Math.sqrt(dx*dx + dy*dy); 
  13.     } 

“這不很容易理解嗎? ” Ruby 問(wèn)道。  

“對(duì)于***次接觸面向?qū)ο缶幊痰娜藖?lái)說(shuō),他分不清這個(gè)當(dāng)前對(duì)象this到底是哪個(gè)對(duì)象?!? Java說(shuō),“我必須得再寫(xiě)一段代碼給他掰扯一下。”  

 
 
 
 
  1. Point p1 = new Point(1,1); 
  2. Point p2 = new Point(2,2); 
  3.  
  4. // this 指向的是p1 
  5. p1.distanceTo(p2);   
  6.  
  7. // this 指向的是p2 
  8. p2.distanceTo(p1);   

“對(duì)啊,this必須得有個(gè)上下文才能準(zhǔn)確理解?!?Python說(shuō),“還有,你那個(gè)this吧,是個(gè)隱式的,像我是顯式的:”  

 
 
 
 
  1. class Point: 
  2.     def __init__(this, x, y): 
  3.         this.x = x 
  4.         this.y = y 
  5.     def distanceTo(this,point): 
  6.         dx = this.x - point.x 
  7.         dy = this.y - point.y 
  8.         return math.sqrt(dx**2+dy**2) 

Java 說(shuō):“你不是一直用self嗎,怎么現(xiàn)在是this?” 

Python笑道:“我這不是為了和你Java老弟保持一致嘛,反正只是個(gè)變量名,你想用this就用this,想用that就用that,只不過(guò)我們習(xí)慣于用self ?!? 

Ruby說(shuō): “Python兄,你把this放到方法中作為一個(gè)參數(shù),實(shí)在是太丑陋了,一點(diǎn)美感都沒(méi)有。”  

“那是我們的哲學(xué),我們信奉 Explicit is better than implicit?!? 

“可是在調(diào)用的時(shí)候,怎么不把一個(gè)對(duì)象傳給那個(gè)方法?你的self去哪里了?”

 
 
 
 
  1. p1 = Point(1,1) 
  2. p2 = Point(2,2) 
  3.  
  4. p1.distanceTo(p2) 
  5. p2.distanceTo(p1) 

 “你怎么不寫(xiě)成: distanceTo(p1,p2) ?” 

 “那不行,” Python說(shuō),“如果那樣的話(huà)我們就不是面向?qū)ο罅?,而面向過(guò)程了。 ”

 “哼哼,” C老頭兒在一旁冷笑一聲,“說(shuō)來(lái)說(shuō)去,還不是披了一層面向?qū)ο蟮耐庖?,?nèi)部實(shí)現(xiàn)依然是面向過(guò)程的?!”  

“此話(huà)怎講?” Java一直以正統(tǒng)的面向?qū)ο笞跃?,不像Python, Ruby ,Java即使是想輸出一個(gè)Hello World也得定義一個(gè)類(lèi)不可。

 “就說(shuō)你吧,Java小子,你的Java 源文件被編譯以后變成了.class文件, 這個(gè)class文件被裝載到了Java虛擬機(jī)的一個(gè)區(qū)域,這個(gè)區(qū)域叫什么?” C 老頭兒出手不凡。 

 “當(dāng)然是Method Area, 方法區(qū)了,這我會(huì)不知道?!”

 “對(duì)啊,它為什么叫方法區(qū)? 為什么不叫Class Area, 類(lèi)區(qū)?”  C 老頭兒真是別出心裁。  

“這…… ”  Java 語(yǔ)噻了,他從來(lái)就沒(méi)有想過(guò)這個(gè)問(wèn)題。

 “你的方法區(qū)是被各個(gè)線(xiàn)程所共享的,存儲(chǔ)虛擬機(jī)加載類(lèi)的信息,常量池,其中最主要的就是類(lèi)中定義的方法相關(guān)的代碼。 而你創(chuàng)建的對(duì)象呢,卻是放在‘堆中’,虛擬機(jī)在執(zhí)行的時(shí)候,要從方法區(qū)找到‘方法’,這些方法的字節(jié)碼在運(yùn)行的過(guò)程中,會(huì)操作位于堆中的對(duì)象。 ” 

 “所以你看,你的數(shù)據(jù)和方法是分離的,一個(gè)地方是方法(所以叫方法區(qū)),一個(gè)地方是數(shù)據(jù),和我們C寫(xiě)出的程序是一樣的,都是面向過(guò)程的!” C老頭兒經(jīng)過(guò)一系列證明后做了最終陳述。

Python也沉默了,他知道,自己在運(yùn)行時(shí)也和這種方式差不多。

過(guò)了一會(huì)兒,Java 醒悟了過(guò)來(lái):“不對(duì),老頭兒你這是混淆概念,我們是站在程序員的角度在談?wù)撜Z(yǔ)言是不是面向?qū)ο蟮?,而你則把我們拉到了實(shí)現(xiàn)層面,這是不對(duì)的?!? 

Python也附和道:“對(duì)對(duì),我們是面向?qū)ο蟮恼Z(yǔ)言,抽象程度比你的面向過(guò)程要高!”

 “抽象? 哼哼,” C 老頭兒又冷笑一聲,“Linus 用C 寫(xiě)了Linux,用C 寫(xiě)了Git, 你覺(jué)得他沒(méi)有做抽象? 笑話(huà)! 依我看來(lái),抽象就是要在變化的東西中找到不變的東西,和具體的編程語(yǔ)言關(guān)系不大啊?!? C老頭說(shuō)了一句至理名言。

Java 悄悄對(duì)Python說(shuō): “老頭兒主要做操作系統(tǒng)內(nèi)核,操作系統(tǒng)中的那些虛擬內(nèi)存,進(jìn)程,線(xiàn)程,文件系統(tǒng)概念都很清晰, 并且很穩(wěn)定,估計(jì)他沒(méi)有接觸到應(yīng)用層變態(tài)的,不講道理的業(yè)務(wù)邏輯。 ”  

C 老頭兒說(shuō):“別以為你們面向?qū)ο笥卸嗝戳瞬黄?,我告訴你,有很多程序員,用著面向?qū)ο蟮恼Z(yǔ)言,寫(xiě)著面向過(guò)程的程序!關(guān)鍵是人!”  

Ruby 說(shuō):“兩位兄臺(tái),算了,不和老頭兒爭(zhēng)論了,來(lái)看看我的this吧, 奧不, 是self, 我這里必須用self。 我的self 和你們的都不一樣,在不同的位置表示不同的含義。比如說(shuō):”

 
 
 
 
  1. class Point 
  2.  
  3.     # 此處的Self 就是Point這個(gè)類(lèi) 
  4.     puts "Self is :#{self}" 
  5.  
  6.     # 定義一個(gè)Class級(jí)別(靜態(tài))的方法,self還是Point這個(gè)類(lèi) 
  7.     def self.name 
  8.         puts "Self inside class method is: #{self}"         
  9.     end 
  10.     # 定義一個(gè)實(shí)例方法, 此處的self 就是對(duì)象實(shí)例了 
  11.     def name 
  12.         puts "Self inside instance method is: #{self}"   
  13.     end 
  14. end 

Java 說(shuō):“你這搞得太麻煩了,定義一個(gè)靜態(tài)方法,用static 不就結(jié)了?”  

半天都沒(méi)有說(shuō)話(huà)的JavaScript突然說(shuō)道:“這也叫麻煩,來(lái)看看我是怎么處理this的!”

 
 
 
 
  1. function add(y){ 
  2.     return this.x + y 

熟悉面向?qū)ο蟮腏ava, Python看到這么古怪的代碼,大為吃驚, 這是什么鬼? add函數(shù)中的這個(gè)this 到底指向誰(shuí)? 

JavaScript說(shuō):“不要大驚小怪! 我的this和你們的this ,self都不一樣,它是動(dòng)態(tài)的,在定義時(shí)確定不了到底指向誰(shuí),只有等到函數(shù)調(diào)用的時(shí)候才能確定,this 指向的是最終調(diào)用它的那個(gè)對(duì)象,比如:” 

 
 
 
 
  1. function add(y){ 
  2.     //此時(shí)的this 指向的是全局的對(duì)象,在瀏覽器運(yùn)行就是window 
  3.     return this.x + y 
  4.  
  5. x = 10 
  6. console.log(add(20)) 

在這里調(diào)用add函數(shù)的是全局上下文, 所以this指向的是全局對(duì)象,輸出的值是30 。 

JavaScript說(shuō):“我還可以給add函數(shù)傳遞一個(gè)對(duì)象當(dāng)作this?!? 

 
 
 
 
  1. function add(y){ 
  2.     //此時(shí)的this 指向的是對(duì)象obj,this.x 是20 ,不是10 
  3.     return this.x + y 
  4.  
  5. x = 10 
  6.  
  7. var obj = {x: 20}; 
  8. //傳遞一個(gè)對(duì)象給add函數(shù) 
  9. add.call(obj,20)  // 40 

大家更加吃驚了。 

JavaScript又展示了一個(gè)例子: 

 
 
 
 
  1. var obj = { 
  2.     x:100, 
  3.     print:function(){ 
  4.        console.log(this.x);  
  5.     }     
  6.  
  7. obj.print() //100 

Python說(shuō): “這個(gè)很容易理解,這個(gè)this應(yīng)該是指向obj這個(gè)對(duì)象實(shí)例, 所以print函數(shù)輸出的x是100,對(duì)吧。” 

“對(duì)的,再來(lái)看一個(gè):”

 
 
 
 
  1. var obj = { 
  2.     x:100, 
  3.     y:{ 
  4.         x : 200, 
  5.         print:function(){ 
  6.             console.log(this.x);  
  7.         } 
  8.     }         
  9. obj.y.print() //200 

Java 說(shuō)道:“按照你的規(guī)則,這個(gè)this 指向的應(yīng)該是最終調(diào)用它的對(duì)象,那就是y , 在y中,x是200,所以應(yīng)該輸出200 !” 

JavaScript說(shuō):“如果我把對(duì)象y中的x:200 給去掉,輸出是什么? ” 

“難道是100 ? 不, 它不會(huì)向上一級(jí)去找,只會(huì)在y中尋找x 的值,如果沒(méi)有,就是undefined, 唉!你這this規(guī)則實(shí)在是太麻煩。” 

 JavaScript笑了笑:“再來(lái)看個(gè)更古怪的例子:”

 
 
 
 
  1. var obj = { 
  2.     x:100, 
  3.     y:{ 
  4.         x : 200, 
  5.         print:function(){ 
  6.             console.log(this.x);  
  7.         } 
  8.     }         
  9.  
  10. var point ={x:15,y:15, f: obj.y.print} 
  11.  
  12. point.f() //輸出什么? 
  13.  
  14. var x = 10 
  15. g = obj.y.print 
  16. g()  //輸出什么? 

Python說(shuō):“這不還是一樣嘛, 都應(yīng)該輸出200。”  

JavaScript說(shuō): “不,point.f() 應(yīng)該輸出15, 注意此時(shí)f 是對(duì)象point的一個(gè)函數(shù),最終調(diào)用f 的是point對(duì)象,此時(shí)x = 15 了!   ”  

Java接口說(shuō):“我明白了,調(diào)用函數(shù)g()的是全局對(duì)象,x = 10 ,所以應(yīng)該輸出10 。” 

Python說(shuō):“你小子號(hào)稱(chēng)前端之王,就這么用this來(lái)折磨程序員?”  

JavaScript笑道:“其實(shí)吧,普通程序員直接操作this的機(jī)會(huì)也不太多,都被框架、類(lèi)庫(kù)封裝好了!”

這時(shí)候就聽(tīng)到C老頭兒在那里搖頭晃腦: “簡(jiǎn)單就是美,簡(jiǎn)單就是美啊。你們這幫小子,把世界搞得這么復(fù)雜,讓程序員們學(xué)習(xí)這么多不必要的復(fù)雜性,真是浪費(fèi)生命啊?!? 

“浪費(fèi)生命? 沒(méi)有我們這些語(yǔ)言,怎么可能創(chuàng)建出這么多Web應(yīng)用程序出來(lái)? 你行嗎?” 

“我是不行,我只知道你Java 虛擬機(jī)是用我C語(yǔ)言寫(xiě)的, 你Python解釋器,Ruby解釋器也是C語(yǔ)言寫(xiě)的, 就連JS的V8引擎也是用我的兄弟C++語(yǔ)言寫(xiě)的。” 

C 老頭兒把手中的咖啡往桌子上狠狠一摔,轉(zhuǎn)身就離開(kāi)了咖啡館。

【本文為專(zhuān)欄作者“劉欣”的原創(chuàng)稿件,轉(zhuǎn)載請(qǐng)通過(guò)作者微信公眾號(hào)coderising獲取授權(quán)】


文章題目:簡(jiǎn)單的this,麻煩的this
本文網(wǎng)址:http://m.5511xx.com/article/dphhcpp.html