Filter 地图上的流和过滤操作

Filter 地图上的流和过滤操作,filter,java-8,java-stream,Filter,Java 8,Java Stream,我有一个EdmPortfolio类型,它有id(int)、name(String)和作为其成员的映射的标记 EdmPortfolioSay的id为1,名称为Portfolio1,Map可以具有以下值, 分析师,约翰 美国地区 我有一个列表,在最后我想有一个地图,它包含所有投资组合的所有地图值。另一个EdmPortfolio可能id为2,名称为Portfolio2,并与价值分析师Smith进行映射 地区,英国 我想要一个带值的组合映射 地区“美国”、“英国” 分析师“约翰”,“史密斯” 分析师和地

我有一个EdmPortfolio类型,它有id(int)、name(String)和作为其成员的映射的标记

EdmPortfolioSay的id为1,名称为Portfolio1,Map可以具有以下值, 分析师,约翰 美国地区

我有一个列表,在最后我想有一个地图,它包含所有投资组合的所有地图值。另一个EdmPortfolio可能id为2,名称为Portfolio2,并与价值分析师Smith进行映射 地区,英国

我想要一个带值的组合映射 地区“美国”、“英国” 分析师“约翰”,“史密斯”

分析师和地区是地图的关键。 它将两张地图合并在一起。我有以下代码,但我有点迷路了

List<Map<Tag,String>> portfolioTagsList = new ArrayList<>();
            for (EdmPortfolio edmPortfolio : edmPortfolioList) {
              Map<Tag,String> portfolioTags =  edmPortfolio.getPortfolioTags().entrySet()
                        .stream()

                        .filter(e -> (e.getValue() != ""|| e.getValue() !=null))
                        .collect(Collectors.toMap(
                                Map.Entry::getKey,
                                Map.Entry::getValue
                        ));


                portfolioTagsList.add(portfolioTags);
            }
            Map<Tag,String> finalTags = portfolioTagsList.stream()
                    .flatMap(m -> m.entrySet().stream())
                    .collect(Collectors.groupingBy(Map.Entry::getKey, Collectors.joining(",",Map.Entry::getValue)));
List portfolioTagsList=new ArrayList();
用于(EdmPortfolio EdmPortfoliost:EdmPortfoliost){
Map-portfolioTags=EdmPortfolioTags.getPortfolioTags().entrySet()
.stream()
.filter(e->(e.getValue()!=“”| | e.getValue()!=null))
.collect(collector.toMap)(
Map.Entry::getKey,
Map.Entry::getValue
));
添加(portfolioTags);
}
Map finalTags=portfolioTagsList.stream()
.flatMap(m->m.entrySet().stream())
.collect(Collectors.groupingBy(Map.Entry::getKey,Collectors.joining(“,”,Map.Entry::getValue));
无法从静态上下文引用非静态方法。我如何做到这一点

谢谢你抽出时间来

我想做一些类似的事情:

Map<Tag,String> finalTags = edmPortfolioList.stream()
.flatMap(edmPortfolio -> edmPortfolio.getPortfolioTags().entrySet().stream())
.filter(e -> (e.getValue() != "" || e.getValue() !=null)) // this seems weird, but just keeping
.collect(Collectors.groupingBy(e -> e.getKey(), 
    Collectors.mapping(ev -> ev.getValue(), 
        Collectors.joining(",")));
Map finalTags=edmPortfolioList.stream()
.flatMap(edmPortfolio->edmPortfolio.getPortfolioTags().entrySet().stream())
.filter(e->(e.getValue()!=“”| | e.getValue()!=null))//这看起来很奇怪,但只是保持
.collect(收集器.groupingBy(e->e.getKey()),
Collectors.mapping(ev->ev.getValue(),
收藏家。加入(“,”);
顺便说一句:有什么理由把它分成两个流吗?

不幸的是,“不能从静态上下文引用非静态方法”是类型推断失败时,
javac
经常出现的错误,特别是在方法引用或lambda表达式的上下文中。实际原因可能是错误的泛型类型参数、忘记的
import
语句、在不适当的位置使用lambda表达式或方法引用,甚至是错误的o我忘在什么地方了

在您的例子中,它是
收集器。加入(“,”,Map.Entry::getValue)
,因为该收集器没有可以接受方法引用的函数类型的参数。
您应该使用
Collectors.mapping(Map.Entry::getValue,Collectors.joining(“,”)


除此之外,请遵循使用单流操作并注意筛选条件。
e.getValue()!=“”| | e.getValue()!=null
没有任何意义,因为引用不能同时是两个,而是对
的引用
null
引用,因此,始终满足此条件。您很可能希望表示字符串不能是
null
且不是空字符串。在这方面,您不应通过引用比较字符串,而应使用
equals
。对于空字符串的测试,可以使用
isEmpty()
而不是
equals(“”
。因此条件应该是
e.getValue()!=null&&!e.getValue().isEmpty()
。注意顺序,因为我们可以调用
isEmpty()
只有在验证了它不是
null

之后,你在哪一行得到了错误?它甚至是你问题中的代码中的一行吗?可能是@Holger的重复,因为OP没有提供确切的错误消息,也没有出现错误的地方,我只是尝试了一个简化版本,推断类型更少,所以相同结果可能会成功实现。顺便说一句,您关于加入的评论很有意义,我相应地编辑了我的答案。OP确实提供了准确的错误消息,尽管不是发生在哪里,而是“无法从静态上下文引用非静态方法”,该位置无论如何都不会有帮助。我经常看到它,并且总是对实际问题的原因感到困惑。将其简化为一个操作确实是一件好事,而且您已经拥有了我的投票权,但对于编译器来说,它增加了更多的推理工作,使得跟踪这个可怕的问题变得更加困难“无法从静态上下文引用非静态方法”错误。我真的希望未来编译器在这方面有所改进……是的,这是有意义的,位置与此错误无关。我现在只是想知道Eclipse Java编译器是否做了一些不同的事情,因为我从来没有在这条消息下报告过此类故障。是的,ECJ的工作方式不同。我看到过误导性错误消息同样,它们在不同的上下文中使用,例如IDE的助手起到了不同的作用,例如Eclipse比Netbeans更急切在插入所需的
import
语句时,不太可能遇到与lambda相关的错误,而该错误实际上是丢失的导入。谢谢。我试图理解并简化它,这就是为什么我将其分为两个流的原因。没有理由,非常感谢您的解释。我也修改了条件。更改为映射成功