मैं स्कैला में कुछ कर्मचारी कर रहा हूं और implicit उदाहरणों के साथ एक समस्या आई। आइए निम्नलिखित उदाहरण पर विचार करें:

import cats.{Applicative, FlatMap, Monad}
import cats.syntax.functor._
import cats.syntax.flatMap._
import cats.syntax.applicative._


class Test[F[_]: Monad] extends App{
  val t1 = ().pure[F]
  val t2 = ().pure[F]

  def testFlatApplicative: F[Unit] =
    for{
      _ <- t1
      _ <- t2
    } yield ()
}

यह ठीक संकलित करता है। लेकिन चूंकि cats.Monad[F[_]] को इस प्रकार घोषित किया गया है:

@typeclass trait Monad[F[_]] extends FlatMap[F] with Applicative[F]

मुझे उम्मीद थी कि निम्नलिखित भी काम करेंगे

import cats.{Applicative, FlatMap, Monad}
import cats.syntax.functor._
import cats.syntax.flatMap._
import cats.syntax.applicative._


class Test[F[_]: FlatMap : Applicative] extends App{
  val t1 = ().pure[F]
  val t2 = ().pure[F]

  def testFlatApplicative: F[Unit] =
    for{
      _ <- t1
      _ <- t2
    } yield ()
}

लेकिन यह त्रुटि के साथ संकलित करने में विफल रहता है:

Error:(16, 12) value map is not a member of type parameter F[Unit]
      _ <- t2

यह अजीब है। Apply बढ़ाता है Functor...

क्या कोई इस व्यवहार की व्याख्या कर सकता है?

3
St.Antario 23 फरवरी 2019, 15:10

1 उत्तर

सबसे बढ़िया उत्तर

class Test[F[_] : FlatMap : Applicative] के लिए desugared है

class Test[F[_]](implicit flatMap: FlatMap[F], applicative: Applicative[F])

यदि आप समझ और वाक्यविन्यास के लिए desugar करते हैं तो आपको समस्या दिखाई देगी:

def testFlatApplicative: F[Unit] = 
  FlatMap[F].flatMap(t1)(_ => 
    Functor[F].map(t2)(_ => ())
  )

Error: ambiguous implicit values:
 both value applicative in class Test of type cats.Applicative[F]
 and value flatMap in class Test of type cats.FlatMap[F]
 match expected type cats.Functor[F]

तो आप अस्पष्टता को मैन्युअल रूप से हल कर सकते हैं:

def testFlatApplicative: F[Unit] = 
  FlatMap[F].flatMap(t1)(_ => 
    applicative.map(t2)(_ => ())
  )

या

def testFlatApplicative: F[Unit] = 
  FlatMap[F].flatMap(t1)(_ => 
    flatMap.map(t2)(_ => ())
  )

जब आप class Test[F[_]: Monad] लिखते हैं तो ऐसी कोई समस्या नहीं है क्योंकि आपके पास एक ही निहित है।

6
Dmytro Mitin 23 फरवरी 2019, 15:33