2014-11-23 74 views
3

我使用ReactiveMongo用MongoDB的一個遊戲框架應用程序,我有以下代碼:創作期貨與理解力

def categories(id: String): Future[Vector[Category]] = {...} 
.... 
val categoriesFuture = categories(id) 
for { 
    categories: Vector[Category] <- categoriesFuture 
    categoryIdsWithoutPerson: Vector[BSONObjectID] <- findCategoryIdsWithoutPerson(categories.map(_.id), personId) //Returns Future[Vector[BSONObjectID]] 
    categoriesWithoutPerson: Vector[Category] <- categories.filter(category => categoryIdsWithoutPerson.contains(category.id)) //Play cites the error here 
} yield categoryIdsWithoutPerson 

爲了解釋這個代碼,我取包裹的Categories一個VectorFuture,因爲這是ReactiveMongo如何滾動。在for的理解中,我使用Vector來從數據庫中獲取一個id列表。最後,我使用一個filter調用來僅保留那些可以在該id列表中找到id的類別。

這一切似乎相當簡單。問題是,遊戲給了我下面的編譯錯誤的for理解的最後一行:

pattern type is incompatible with expected type; 
found : Vector[com.myapp.Category] 
required: com.myapp.Category 

我不知道爲什麼所需的類型是Category一個實例。

我可以使用一些洞察力來了解我在做什麼錯誤和/或是否有更簡單或更習慣的方式來完成此操作。

+0

你可以張貼的 '類別' 方法的簽名?以及在哪一行檢測到錯誤? – ale64bit 2014-11-23 21:47:31

+0

按要求澄清。謝謝。 – Vidya 2014-11-23 21:59:15

+0

只是好奇,爲什麼你產生categoryIdsWithoutPerson爲結果?什麼是理解的最後一行? – ale64bit 2014-11-23 22:02:28

回答

5

它看起來像你想編寫FuturesVector。對於scala的理解必須都是相同的更高類型,在你的情況下是Future。當你展開理解的'糖'時,它只需要調用flatMap就可以了。

for { 
    categories <- categoriesFuture 
    // I'm not sure what the return type is here, but I'm guessing it's a future as well 
    categoryIdsWithoutPerson <- findCategoryIdsWithoutPerson(categories.map(_.id), personId) 
    // Here we use = to get around need to flatMap 
    categoriesWithoutPerson = categories.filter(category => categoryIdsWithoutPerson.contains(category.id)) 
} yield categoryIdsWithoutPerson 

你的代碼去加糖:

categoriesFuture.flatMap(categories => 
    findCategoryIdsWithoutPerson(categories.map(_.id), personId). 
    flatMap(categoryIdsWithoutPerson => 
     categories.filter(category => categoryIdsWithoutPerson.contains(category.id)). 
      map(_ => categoryIdsWithoutPerson))