2010-09-22 78 views

回答

47

忽略嵌套函數,始終可以用沒有返回值的等價計算替換Scala計算。這個結果可以追溯到「結構化編程」的初期,巧妙地稱爲structured program theorem

使用嵌套函數,情況發生變化。 Scala允許你放置一系列嵌套函數深處的「返回」。當執行返回時,控制從所有嵌套函數跳轉到最裏面的包含方法,並從中返回(假設方法實際上仍在執行,否則拋出異常)。這種堆棧展開可以使用異常完成,但不能通過機械重構計算來完成(可能沒有嵌套函數)。

你實際上想從嵌套函數中返回的最常見原因是打破理解或資源控制塊的必要性。 (一個刻不容緩-理解的身體被轉換到一個嵌套函數,即使它看起來就像一個聲明。)

for(i<- 1 to bezillion; j <- i to bezillion+6){ 
if(expensiveCalculation(i, j)){ 
    return otherExpensiveCalculation(i, j) 
} 

withExpensiveResource(urlForExpensiveResource){ resource => 
// do a bunch of stuff 
if(done) return 
//do a bunch of other stuff 
if(reallyDoneThisTime) return 
//final batch of stuff 
} 
+0

感謝您的回答。這是非常豐富的。 – Jus12 2010-09-23 16:07:32

+0

我認爲這是一個更正式的答案。我對你提到的結果證明感興趣。你能提供一些參考嗎? – Jus12 2010-09-23 18:52:12

+0

爲結構化程序定理添加了維基百科的鏈接。 – 2010-09-23 20:15:54

26

提供它以適應那些將所有控制流路徑安排在該方法的詞彙端聚合困難或麻煩的情況。

雖然Dave Griffith說的確可以消除return的任何使用,但這樣做通常會更迷惑人,而不是簡單地用明顯的return將執行縮短。

請注意,return也是從方法返回的,而不是函數(文字),可能在方法中定義。

+0

我知道這是答案..我只是想不出任何例子。 – Jus12 2010-09-22 16:04:35

+8

對我來說幸運的是,你沒有要求任何例子...... – 2010-09-22 16:07:45

+0

+1 for obfuscatory – 2012-01-07 01:39:08

2

我認爲return作爲一個有用的寫命令行式風格的代碼,這通常意味着我的時候/ O代碼。如果你正在做純功能代碼,你不需要(也不應該使用)return。但是對於功能代碼,您可能需要懶惰才能獲得與使用return可以「儘早退出」的命令式代碼相當的性能。

3

下面是一個例子

這種方法有很多的if-else語句來控制流量,因爲沒有回報(這就是我來了,你可以用你的想象力把它擴大)。我把這個從現實生活中的例子,並修改它是僞代碼(實際上比這更長):

不退還:

def process(request: Request[RawBuffer]): Result = { 
     if (condition1) { 
     error() 
     } else { 
     val condition2 = doSomethingElse() 
     if (!condition2) { 
      error() 
     } else { 
      val reply = doAnotherThing() 
      if (reply == null) { 
      Logger.warn("Receipt is null. Send bad request") 
      BadRequest("Coudln't receive receipt") 
      } else { 
      reply.hede = initializeHede() 
      if (reply.hede.isGood) { 
       success() 
      } else { 
       error() 
      } 
      } 
     } 
     } 
    } 

有了回報:

def process(request: Request[RawBuffer]): Result = { 
     if (condition1) { 
     return error() 
     } 

     val condition2 = doSomethingElse() 
     if (!condition2) { 
     return error() 
     } 

     val reply = doAnotherThing() 

     if (reply == null) { 
     Logger.warn("Receipt is null. Send bad request") 
     return BadRequest("Coudln't receive receipt") 
     } 

     reply.hede = initializeHede() 
     if (reply.hede.isGood) 
     return success() 

     return error() 
    } 

在我看來,第二個比第一個更可讀,更易於管理。如果不使用返回語句,則縮進深度(格式良好的代碼)深入深入。我不喜歡它:)

+2

我認爲經驗豐富的Scala程序員(不是我)可以更清楚地遵循第一個片段。 – Jus12 2016-02-07 13:06:45

+0

確實這是一種「品味」,取決於開發者的觀點。例如我最喜歡平底鞋 – yerlilbilgin 2017-07-18 00:47:34