मान लीजिए आपको पहले पांच पोस्ट का उपयोगकर्ता नाम प्राप्त करने की आवश्यकता है। आप जल्दी से नीचे प्रश्न लिखें और अपने सप्ताहांत का आनंद लें।
posts = Post.limit(5)
posts.each do |post|
puts post.user.name
end
अच्छा। लेकिन आइए प्रश्नों को देखें
Post Load (0.5ms) SELECT `posts`.* FROM `posts` LIMIT 5
User Load (0.3ms) SELECT `users`.* FROM `users` WHERE `users`.`id` = 1 LIMIT 1
User Load (0.3ms) SELECT `users`.* FROM `users` WHERE `users`.`id` = 1 LIMIT 1
User Load (0.3ms) SELECT `users`.* FROM `users` WHERE `users`.`id` = 2 LIMIT 1
User Load (0.3ms) SELECT `users`.* FROM `users` WHERE `users`.`id` = 2 LIMIT 1
User Load (0.3ms) SELECT `users`.* FROM `users` WHERE `users`.`id` = 1 LIMIT 1
1 query सभी posts लाने के लिए और 1 query users प्रत्येक पोस्ट के परिणाम कुल 6 queries . में होते हैं . नीचे दिए गए समाधान की जाँच करें जो वही काम करता है, बस 2 queries . में :
posts = Post.includes(:user).limit(5)
posts.each do |post|
puts post.user.name
end
#####
Post Load (0.3ms) SELECT `posts`.* FROM `posts` LIMIT 5
User Load (0.3ms) SELECT `users`.* FROM `users` WHERE `users`.`id` IN (1, 2)
एक छोटा सा अंतर है। जोड़ें includes(:posts) आपकी क्वेरी के लिए, और समस्या हल हो गई। तेज़, अच्छा और आसान।
लेकिन न केवल includes आपकी क्वेरी में इसे ठीक से समझे बिना। includes . का उपयोग करना joins . के साथ स्थिति के आधार पर क्रॉस-जॉइन हो सकता है, और ज्यादातर मामलों में आपको इसकी आवश्यकता नहीं होती है।
यदि आप अपने शामिल मॉडलों में शर्तें जोड़ना चाहते हैं तो आपको उनका स्पष्ट रूप से संदर्भ देना होगा . उदाहरण के लिए:
User.includes(:posts).where('posts.name = ?', 'example')
एक त्रुटि देगा, लेकिन यह काम करेगा:
User.includes(:posts).where('posts.name = ?', 'example').references(:posts)
ध्यान दें कि includes association names के साथ काम करता है जबकि references the actual table name की आवश्यकता है ।