根据其他列表流式传输和过滤一个列表

时间:2017-05-30 22:24:30

标签: java list java-8

我有一个对象列表。这些对象有一个字符串变量。我还有一个字符串列表。

就像这样。

def read_thread(conn, f):
    conn.cursor().copy_expert("COPY foo TO STDIN;", f)
    f.close()
    conn.close()

engine.execute(
    "CREATE TABLE foo(id int);"
    "CREATE TABLE bar(id int);"
    "INSERT INTO foo (SELECT generate_series(1, 100000) AS id);"
    "COMMIT;")
input_conn = engine.raw_connection()
output_conn = engine.raw_connection()
pipe = FilePipe()

t = Thread(target=read_thread, args=(input_conn, pipe.input))
t.start()
output_cur = output_conn.cursor()
output_cur.copy_expert("COPY bar FROM STDIN;", pipe.output)
output_conn.commit()
output_conn.close()
t.join()

print(list(engine.execute("SELECT count(*) FROM bar;")))  # 100000

我希望能够做的是根据x是否包含列表B中的任何字符串对象来流式传输和过滤listA。

这可行吗?

3 个答案:

答案 0 :(得分:3)

List<A> filtered = 
    listA.stream()
         .filter(a -> listB.stream().anyMatch(b -> x.a.contains(b)))
         .collect(Collectors.toList());

答案 1 :(得分:1)

当然 - 只需在contains子句中调用filter

List<A> filtered = 
    listA.stream().filter(a -> listB.contains(a.x)).collect(Collectors.toList());

答案 2 :(得分:1)

您应该使用HashSet来存储String值。原因是HashSet保证O(1)或恒定时间查找。使用列表,它是O(n),这意味着查找(.contains)需要在最坏的情况下迭代其所有元素。

因此,以下方法将更有效:

List<A> listA ...
Set<String> setB = new HashSet<>(); // populate setB
List<A> filteredA =
    listA.stream()
        .filter(a -> setB.contains(a.x)).collect(toList());

另请参阅this答案,了解性能差异的一些具体证据。