2014-12-18 5 views
6

चलो कुछ स्कालाज़-स्ट्रीम दस्तावेज़ों से एक उदाहरण लें, लेकिन सैद्धांतिक मोड़ के साथ।स्केलज़-स्ट्रीम में कार्य से अपवाद को लॉगिंग और अनदेखा करना

import scalaz.stream._ 
import scalaz.concurrent.Task 

val converter: Task[Unit] = 
    io.linesR("testdata/fahrenheit.txt") 
    .filter(s => !s.trim.isEmpty && !s.startsWith("//")) 
    .map(line => fahrenheitToCelsius(line.toDouble).toString) 
    .intersperse("\n") 
    .pipe(text.utf8Encode) 
    .to(io.fileChunkW("testdata/celsius.txt")) 
    .run 

// at the end of the universe... 
val u: Unit = converter.run 

इस मामले में फ़ाइल बहुत अच्छी तरह से कुछ गैर डबल स्ट्रिंग शामिल हो सकता है, और fahrenheitToCelsius कुछ NumberFormatException फेंक देते हैं। आइए मान लें कि इस मामले में हम शायद इस त्रुटि को लॉग करना चाहते हैं और आगे स्ट्रीम प्रोसेसिंग के लिए इसे अनदेखा करना चाहते हैं। ऐसा करने का बेवकूफ तरीका क्या है? मैंने कुछ उदाहरण देखे हैं, लेकिन वे आमतौर पर collectFrom स्ट्रीम करते हैं।

+0

शायद Scalaz के लिए बहुत मुहावरेदार नहीं कदम है, लेकिन आप मानचित्रण के लिए और मामले में यह विफल रहा है 'Try' उपयोग कर सकते हैं, त्रुटि लॉग ऑन रास्ता आप चाहते हैं (शायद इस तरह: https://github.com/scalaz/scalaz-stream/blob/master/src/test/scala/scalaz/stream/examples/WritingAndLogging.scala#L63)। –

उत्तर

3

आप scalaz साथ यह कर सकते हैं। \/और अतिरिक्त संसाधन

def fahrenheitToCelsius(line: String): Throwable \/ String = 
    \/.fromTryCatchNonFatal { 
     val fahrenheit = line.toDouble 
     val celsius = fahrenheit // replace with real convert 
     celsius.toString 
    } 

    def collectSome[T]: PartialFunction[Option[T], T] = { 
    case Some(v) => v 
    } 

    def logThrowable[T]: PartialFunction[Throwable \/ T, Option[T]] = { 
    case -\/(err) => 
     err.printStackTrace() 
     None 
    case \/-(v) => Some(v) 
    } 

    val converter: Task[Unit] = 
    io.linesR("testdata/fahrenheit.txt") 
     .filter(s => !s.trim.isEmpty && !s.startsWith("//")) 
     .map(fahrenheitToCelsius) 
     .map(logThrowable) 
     .collect(collectSome) 
     .intersperse("\n") 
     .pipe(text.utf8Encode) 
     .to(io.fileChunkW("testdata/celsius.txt")) 
     .run 
+0

ठीक है, तो कोई रन/प्रयास नहीं है निष्पादक या एक सामान्य हैंडलर जिसे कुछ अपवादों पर कार्य करने के लिए निर्दिष्ट किया जा सकता है? साथ ही, मुझे लगता है कि '.map (collectCome)' इस मामले में '.collect (collectSome)' होना चाहिए। डिफ़ॉल्ट प्रक्रिया द्वारा – kareblak

+0

पहले अपवाद पर असफल हो जाएगा, लेकिन मुझे लगता है कि आप उन्हें सभी लॉग करना चाहते हैं, इसलिए आपको असफल होने वाले प्रत्येक चरण पर अपवादों को पकड़ने की आवश्यकता है। हाँ, यह एक टाइपो है, इकट्ठा किया जाना चाहिए (संग्रह कुछ) –

+0

हां, आईओ पढ़ने के लिए बहुत आसान है, जिसके लिए स्केलज-स्ट्रीम बहुत अधिक बनाये जाते हैं, खासकर यदि आपके पास डेटा पढ़ने और गुणवत्ता की गुणवत्ता पर कोई नियंत्रण नहीं है आँकड़े। यह एक धारा है - कुछ मामलों में आप भ्रष्ट सामान को फेंकना चाहते हैं। लेकिन जवाब वास्तव में कवर है। – kareblak

संबंधित मुद्दे