Tworzenie streamu z kolekcji a n+1

0

mamy encje, która ma w sobie zaleznosc many-to-one, robiac stream z tej kolekcji

@Entity
 public class RegisteredUser {

 

    @JsonManagedReference
    @OneToMany(mappedBy = "user")
    private Set<Tweet> tweets;

robiac teraz

  RegisteredUser tweetOwner = userRepository.findOne(1);
        Tweet searchedTweet = tweetOwner
                .getTweets()
                .stream().forEach(coś tam)
  1. bedzie n+1?

2.Czy operacje filtorwania lepiej wykonywac w sql querries czy filtrowac np kolekcje po odpowiednim predykacie?

1

ad 1. Będzie 1+1 i dobrze
(n+1 byłoby gdybyś miał listę RegisteredUser i dla każdego elementu z listy zbierał Tweety)

ad 2. To zależy. Jak masz tysiące obiektów do filtrowania to zwykle lepiej je przenieść do SQL query, poniżej 100 natomiast jest raczej wszystko jedno (a w javie czesto prościej).

1

@jarekr000000 oj nie jestem taki pewny, bo on nie pyta o to czy w swoim kodzie zrobił n+1, bo to oczywiste ze nie ;) On pyta czy silnik JPA pod spodem czasem nie będzie pobierał elementów setu osobnymi query w trakcie iteracji i niestety obawiam sie że będzie jeśli ten set jest lazy.
@filemonczyk włącz logowanie i zobacz ile query leci dla tej operacji, ale licz się z tym że może trzeba będzie tam zrobić jakiś fetch join żeby pobrać całą kolekcje w jednym query.

0

Tak się własnie zastanawialem, czy operujac na streamie, nie wywołamy pośrednio n+1 jak w przypadku normalnej iteracji

 spring.jpa.show-sql = true

wywoluje metode:

RegisteredUser tweetOwner = userRepository.findOne((long)1);
         tweetOwner
                .getTweets()
                .forEach(System.out::println);

logi


Hibernate: select registered0_.user_id as user_id1_0_0_, registered0_.email as email2_0_0_, registered0_.first_name as first_na3_0_0_, registered0_.last_name as last_nam4_0_0_, registered0_.password as password5_0_0_, registered0_.www as www6_0_0_, roles1_.registered_user_id as register3_1_1_, roles1_.role_id as role_id1_1_1_, roles1_.role_id as role_id1_1_2_, roles1_.role as role2_1_2_, roles1_.registered_user_id as register3_1_2_ from registered_user registered0_ left outer join role roles1_ on registered0_.user_id=roles1_.registered_user_id where registered0_.user_id=?
Hibernate: select tweets0_.user_id as user_id4_2_0_, tweets0_.tweet_id as tweet_id1_2_0_, tweets0_.tweet_id as tweet_id1_2_1_, tweets0_.content as content2_2_1_, tweets0_.score as score3_2_1_, tweets0_.user_id as user_id4_2_1_ from tweet tweets0_ where tweets0_.user_id=?
twitter.model.Tweet@75b20340
twitter.model.Tweet@647ab628
twitter.model.Tweet@2a2fecf8
twitter.model.Tweet@18a046aa
twitter.model.Tweet@207dccd1
twitter.model.Tweet@7e75391b
twitter.model.Tweet@1bb88d96

czyli nie ma n+1,

0

@filemonczyk no bo tam u góry masz kolekcje EAGER (default) a nie LAZY, więc łyknie ją w całości. Ale pamiętaj jakie jest ryzyko -> że wyrwiesz kiedys pół bazy danych jednym głupim selectem.

1 użytkowników online, w tym zalogowanych: 0, gości: 1