मान लीजिए आपको पहले पांच पोस्ट का उपयोगकर्ता नाम प्राप्त करने की आवश्यकता है। आप जल्दी से नीचे प्रश्न लिखें और अपने सप्ताहांत का आनंद लें।
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
की आवश्यकता है ।