2016-10-01 77 views
-1

我想重構我的方法,它過濾AssetLink對象,獲取作爲AssetLink目標的Content對象,然後根據Content對象設置ContentLinkMetadata對象的字段。我的新方法看起來像這樣:Java 8 - 方法映射不適用於參數(<noType>)

private List<ContentLinkMetadata> getAndFillInternalLinks(final Lesson lesson) { 
    List<ContentLinkMetadata> internalLinks = new ArrayList<>(); 
     lesson.getAssetLinks().stream() 
     .filter(linkAsAssetLink -> ALLOWED_INTERNAL_LINK_TYPES.contains(linkAsAssetLink.getTargetType())) 
     .map(linkAsAssetLink -> { 
      Content link = contentProvider.getLazyById(linkAsAssetLink.getTargetId()); 
      ContentLinkMetadata internalLink = new ContentLinkMetadata(); 

      internalLink.setDescription(link.getDescription()); 
      internalLink.setId(link.getId()); 
      internalLink.setTitle(link.getTitle()); 
      internalLink.setFriendlyUrl(friendlyUrlResolver.makeUrl(link)); 
      internalLink.setTypeId(link.getTypeId()); 

      internalLinks.add(internalLink); 
     }); 

     return internalLinks; 
} 

但是我卻越來越對.MAP錯誤,說:「在Stream類型的方法映射是不適用的參數(NoType在linkAsAssetLink),我不明白這一點。爲什麼它說linkAsAssetLink是「noType」,實際上是AssetLink,我可以在contentProvider的方法中使用它的方法。你能告訴我我在哪裏犯了一個錯誤嗎?

回答

1

看起來你錯了。有以下幾種方式

private List<ContentLinkMetadata> getAndFillInternalLinks(final Lesson lesson) { 
    List<ContentLinkMetadata> internalLinks = lesson.getAssetLinks().stream() 
     .filter(linkAsAssetLink -> ALLOWED_INTERNAL_LINK_TYPES.contains(linkAsAssetLink.getTargetType())) 
     .map(linkAsAssetLink -> { 
      Content link = contentProvider.getLazyById(linkAsAssetLink.getTargetId()); 
      ContentLinkMetadata internalLink = new ContentLinkMetadata(); 

      internalLink.setDescription(link.getDescription()); 
      internalLink.setId(link.getId()); 
      internalLink.setTitle(link.getTitle()); 
      internalLink.setFriendlyUrl(friendlyUrlResolver.makeUrl(link)); 
      internalLink.setTypeId(link.getTypeId()); 

      return internalLink; 
     }).collect(Collectors.toList()); 

     return internalLinks; 
} 

或者你可以用f oreach以及:

private List<ContentLinkMetadata> getAndFillInternalLinks(final Lesson lesson) { 
    List<ContentLinkMetadata> internalLinks = new ArrayList<>(); 
     lesson.getAssetLinks().stream() 
     .filter(linkAsAssetLink -> ALLOWED_INTERNAL_LINK_TYPES.contains(linkAsAssetLink.getTargetType())) 
     .map(linkAsAssetLink -> { 
      Content link = contentProvider.getLazyById(linkAsAssetLink.getTargetId()); 
      ContentLinkMetadata internalLink = new ContentLinkMetadata(); 

      internalLink.setDescription(link.getDescription()); 
      internalLink.setId(link.getId()); 
      internalLink.setTitle(link.getTitle()); 
      internalLink.setFriendlyUrl(friendlyUrlResolver.makeUrl(link)); 
      internalLink.setTypeId(link.getTypeId()); 

      return internalLink; 
     }).foreach(internalLinks::add); 

     return internalLinks; 
} 

地圖總是應該返回一些東西。返回語句可以是隱式的,但它應該在那裏。

3

如果在操作圖中使用括號,則應使用返回運算符。你的代碼應該是這個樣子

private List<ContentLinkMetadata> getAndFillInternalLinks(final Lesson lesson) { 
List<ContentLinkMetadata> internalLinks = lesson.getAssetLinks().stream() 
    .filter(linkAsAssetLink -> ALLOWED_INTERNAL_LINK_TYPES.contains(linkAsAssetLink.getTargetType())) 
    .map(linkAsAssetLink -> { 
     Content link = contentProvider.getLazyById(linkAsAssetLink.getTargetId()); 
     ContentLinkMetadata internalLink = new ContentLinkMetadata(); 
     internalLink.setDescription(link.getDescription()); 
     internalLink.setId(link.getId()); 
     internalLink.setTitle(link.getTitle()); 
     internalLink.setFriendlyUrl(friendlyUrlResolver.makeUrl(link)); 
     internalLink.setTypeId(link.getTypeId()); 
     return internalLink; 
    }).collect(Collectors.toList()); 

}

或使用該代碼

List<ContentLinkMetadata> internalLinks = lesson.getAssetLinks().stream() 
     .filter(linkAsAssetLink -> ALLOWED_INTERNAL_LINK_TYPES.contains(linkAsAssetLink.getTargetType())) 
     .map(linkAsAssetLink -> linkAsAssetLink.getTargetId()) 
     .filter(Objects::nonNull) 
     .map(function) 
     }).collect(Collectors.toList()) 


private Function<Object, ContentLinkMetadata> function = this::toInternalLink; 

private ContentLinkMetadata toInternalLink(Object linkAsAssetLink){ 
       Content link = contentProvider.getLazyById(linkAsAssetLink.getTargetId()); 
       ContentLinkMetadata internalLink = new ContentLinkMetadata(); 
       internalLink.setDescription(link.getDescription()); 
       internalLink.setId(link.getId()); 
       internalLink.setTitle(link.getTitle()); 
       internalLink.setFriendlyUrl(friendlyUrlResolver.makeUrl(link)); 
       internalLink.setTypeId(link.getTypeId()); 
       return internalLink; 
}