2012-04-18 9 views
5

मैं तालिका से लगभग 100 मिलियन पंक्तियों को पुनर्प्राप्त करने के लिए हाइबरनेट का उपयोग करने की कोशिश कर रहा हूं। मेरे पास एक स्थिर इकाई वस्तु है जिसमें फीस का संग्रह शामिल है (एक और स्थिर इकाई)। यह देखते हुए कि मैं परिणाम पर पुन: प्रयास करता हूं और प्रत्येक ऑब्जेक्ट के लिए शुल्क तक पहुंचता हूं, मैं उत्सुकता से एन + 1 समस्या से बचने के लिए शुल्क लेना चाहता हूं।स्क्रॉल करने योग्य रीसेट्स के साथ हाइबरनेट में उत्सुक संग्रह संग्रह

मुझे यह भी उल्लेख करना चाहिए कि मैं इसे प्रदाता (एक-से-एक मैपिंग लेकिन कोई विदेशी कुंजी) नामक किसी अन्य तालिका में शामिल नहीं करना चाहता हूं। मैंने कोशिश की:

String query = "select new " + Order.class.getName() 
      + "(i, p) from Item i left join fetch i.fees f, Provider p where " 
      + "p.factoryId=i.factoryId and p.factoryRef=i.factoryRef"; 

return session.createQuery(query).scroll(); 

मेरे आदेश वर्ग एक प्रदाता क्षेत्र और एक आइटम फ़ील्ड है।

Caused by: org.hibernate.QueryException: query specified join fetching, but the owner of the fetched association was not present in the select list

मैं आदेश जो मद और प्रदाता (फीस बेसब्री से प्राप्त किए गए) के साथ शामिल की एक स्क्रॉल सूची के साथ अंत करना चाहते हैं: मैं इस त्रुटि मिलती है।

उत्तर

1

SelectClause से इस कोड को आप मुसीबत का कारण बनता है। fromElementsForLoad.contains(origin)

उन्होंने शायद आपको अनावश्यक रूप से शामिल होने से बचाने के लिए ऐसा किया है जो आपको प्रदर्शन में बहुत अधिक खर्च करेगा। यह एक अच्छी बात है क्योंकि यदि आप इसका कभी भी उपयोग नहीं करते हैं तो एसोसिएशन लाने का कोई कारण नहीं है।

मुझे विश्वास है कि आपके मामले में - नई Order.class में Item.class लपेटकर तथ्य यह है कि आप क्वेरी में लाने सजाया क्षेत्र माता पिता का उपयोग करते हैं छुपाता है।

इस समय मेरे पास कोई डिबगिंग क्षमता नहीं है इसलिए मैं इसे सत्यापित नहीं कर सकता। SelectClause.class से इस सटीक पंक्ति को आज़माएं और डीबग करें और देखें कि fromElementsForLoad संग्रह में कौन से तत्व संग्रह हैं।

यदि आप एन + 1 समस्या से बचना चाहते हैं तो मैं क्वेरी के बाद ऑर्डर.क्लास शुरू करने की सलाह दूंगा। आप केवल आइटम और प्रदाता का चयन कर सकते हैं।

यदि आप इसे मान्य नहीं कर सकते हैं, तो मैं अगले सप्ताह एक उचित कंप्यूटर पर जाऊंगा और अपना उत्तर विस्तारित करूंगा।

+0

मुझे लगता है कि यह उत्तर सही है। यदि ऐसा है, तो आपको हाइबरनेट को यह जानने में सक्षम होना चाहिए कि आप 'ऑर्डर' बनाने के बजाए 'सूची' वापस करने के लिए क्वेरी को बदलकर 'आइटम' को वापस ला रहे हैं: 'i, p से चुनें ...'। इसके बाद आपको 'ऑर्डर मैन्युअल रूप से बनाना होगा। –

0

left join fetch i.fees f को हटाने का प्रयास करें और मैपिंग में उत्सुकता प्राप्त करें।

if (!fromElementsForLoad.contains(origin)) { 
         throw new QueryException(
           "query specified join fetching, but the owner " + 
           "of the fetched association was not present in the select list " + 
           "[" + fromElement.getDisplayText() + "]" 
         ); 

आप देख सकते हैं, जब लाने कीवर्ड उल्लेख किया गया है, देखने के लिए अगर आप लाने सजाया क्षेत्र माता पिता के लिए कहा चेकों हाइबरनेट:

संबंधित मुद्दे