java - "मुख्य वर्ग को ढूंढ या लोड नहीं किया जा सकता" का क्या अर्थ है?




class main (20)

एक सामान्य समस्या है कि नए जावा डेवलपर्स का अनुभव यह है कि उनके प्रोग्राम त्रुटि संदेश के साथ चलाने में असफल होते हैं: Could not find or load main class ...

इसका क्या अर्थ है, इसका कारण क्या है, और आपको इसे कैसे ठीक करना चाहिए?


java <class-name> कमांड सिंटैक्स

सबसे पहले, आपको java (या java ) कमांड का उपयोग करके प्रोग्राम लॉन्च करने के सही तरीके को समझने की आवश्यकता है।

सामान्य वाक्यविन्यास 1 यह है:

    java [ <option> ... ] <class-name> [<argument> ...]

जहां <option> एक कमांड लाइन विकल्प है (एक "-" वर्ण से शुरू होता है), <class-name> एक पूर्णतः योग्य जावा क्लास नाम है, और <argument> एक मनमानी कमांड लाइन तर्क है जो आपके एप्लिकेशन को पास हो जाता है।
1 - "निष्पादन योग्य" जेएआर फाइलों के लिए दूसरा वाक्यविन्यास है जिसे मैं नीचे वर्णित करूंगा।

कक्षा के लिए पूरी तरह से योग्य नाम (एफक्यूएन) परंपरागत रूप से लिखा गया है जैसा कि आप जावा स्रोत कोड में करेंगे; जैसे

    packagename.packagename2.packagename3.ClassName

हालांकि java कमांड के कुछ संस्करण आपको अवधि के बजाए स्लेश का उपयोग करने की अनुमति देते हैं; जैसे

    packagename/packagename2/packagename3/ClassName

जो (भ्रमित) फ़ाइल पथनाम की तरह दिखता है, लेकिन एक नहीं है। ध्यान दें कि शब्द पूरी तरह से योग्य नाम मानक जावा शब्दावली है ... कुछ ऐसा नहीं जो मैंने अभी आपको भ्रमित करने के लिए बनाया है :-)

यहां एक उदाहरण दिया गया है कि java कमांड कैसा दिखना चाहिए:

    java -Xmx100m com.acme.example.ListUsers fred joe bert

उपरोक्त java कमांड को निम्नलिखित करने का कारण बन रहा है:

  1. com.acme.example.ListUsers क्लास के संकलित संस्करण के लिए खोजें।
  2. कक्षा लोड करें।
  3. जांचें कि कक्षा में public static void main(String[]) द्वारा दिए गए हस्ताक्षर , रिटर्न प्रकार और संशोधक के साथ एक main विधि है। (ध्यान दें, विधि तर्क का नाम हस्ताक्षर का हिस्सा नहीं है ।)
  4. String[] रूप में कमांड लाइन तर्क ("fred", "joe", "bert") को पास करने वाली विधि को उस विधि को कॉल करें।

कारण क्लास कक्षा क्यों नहीं ढूंढ सकता है

जब आपको संदेश मिलता है "मुख्य वर्ग नहीं मिला या लोड नहीं हो सका ...", इसका मतलब है कि पहला कदम विफल हो गया है। java कमांड कक्षा को खोजने में सक्षम नहीं था। और वास्तव में, संदेश में "..." पूरी तरह से योग्य वर्ग का नाम होगा जिसे java ढूंढ रहा है।

तो कक्षा को खोजने में असमर्थ क्यों हो सकता है?

कारण # 1 - आपने वर्गनाम तर्क के साथ गलती की है

पहला संभावित कारण यह है कि आपने गलत वर्ग का नाम प्रदान किया हो सकता है। (या ... सही वर्ग का नाम, लेकिन गलत रूप में।) ऊपर दिए गए उदाहरण को ध्यान में रखते हुए, कक्षा नाम निर्दिष्ट करने के लिए कई गलत तरीके यहां दिए गए हैं:

  • उदाहरण # 1 - एक साधारण वर्ग का नाम:

    java ListUser
    

    जब क्लास को com.acme.example जैसे पैकेज में घोषित किया जाता है, तो आपको java कमांड में पैकेज नाम सहित पूर्ण श्रेणी नाम का उपयोग करना होगा; जैसे

    java com.acme.example.ListUser
    
  • उदाहरण # 2 - कक्षा नाम के बजाय एक फ़ाइल नाम या पथनाम:

    java ListUser.class
    java com/acme/example/ListUser.class
    
  • उदाहरण # 3 - आवरण के साथ एक वर्ग का नाम गलत:

    java com.acme.example.listuser
    
  • उदाहरण # 4 - एक टाइपो

    java com.acme.example.mistuser
    
  • उदाहरण # 5 - एक स्रोत फ़ाइल नाम

    java ListUser.java
    
  • उदाहरण # 6 - आप कक्षा का नाम पूरी तरह से भूल गए हैं

    java lots of arguments
    

कारण # 2 - एप्लिकेशन का क्लासपाथ गलत तरीके से निर्दिष्ट है

दूसरा संभावित कारण यह है कि कक्षा का नाम सही है, लेकिन java कमांड कक्षा नहीं ढूंढ सकता है। इसे समझने के लिए, आपको "क्लासपाथ" की अवधारणा को समझने की आवश्यकता है। यह ओरेकल दस्तावेज द्वारा अच्छी तरह से समझाया गया है:

तो ... यदि आपने कक्षा का नाम सही तरीके से निर्दिष्ट किया है, तो जांच करने की अगली बात यह है कि आपने क्लासपाथ को सही तरीके से निर्दिष्ट किया है:

  1. ऊपर जुड़े तीन दस्तावेज पढ़ें। (हाँ ... उन्हें पढ़ें। यह महत्वपूर्ण है कि जावा प्रोग्रामर कम से कम मूलभूत बातें समझता है कि जावा क्लासपाथ तंत्र कैसे काम करता है।)
  2. जब आप java कमांड चलाते हैं तो कमांड लाइन और / या क्लास्स्पैट पर्यावरण चर को देखें। जांचें कि निर्देशिका नाम और जेएआर फ़ाइल नाम सही हैं।
  3. यदि क्लासपाथ में सापेक्ष पथनाम हैं, तो जांचें कि वे सही तरीके से हल करते हैं ... वर्तमान निर्देशिका से जो प्रभावशाली है जब आप java कमांड चलाते हैं।
  4. जांचें कि वर्ग (त्रुटि संदेश में उल्लिखित) प्रभावी क्लासपाथ पर स्थित हो सकता है।
  5. ध्यान दें कि क्लासपाथ सिंटैक्स विंडोज बनाम लिनक्स और मैक ओएस के लिए अलग है

कारण # 2 ए - गलत निर्देशिका क्लासपाथ पर है

जब आप कक्षापथ पर एक निर्देशिका डालते हैं, तो यह अनुमानित रूप से योग्य नाम स्थान की जड़ से मेल खाता है। वर्ग पथ के नीचे पूरी तरह से योग्य नाम मैप करके , रूट के नीचे निर्देशिका संरचना में स्थित हैं। तो उदाहरण के लिए, यदि वर्ग पथ पर "/ usr / local / acme / classes" वर्ग है, तो जब JVM com.acme.example.Foon नामक कक्षा की com.acme.example.Foon , तो यह इसके साथ ".class" फ़ाइल की तलाश करेगा पथ नाम:

  /usr/local/acme/classes/com/acme/example/Foon.class

यदि आपने क्लासपाथ पर "/ usr / local / acme / classes / com / acme / example" रखा था, तो JVM कक्षा को नहीं ढूंढ पाएगा।

कारण # 2 बी - उपनिर्देशिका पथ FQN से मेल नहीं खाता है

यदि आपकी कक्षाएं FQN com.acme.example.Foon है, तो JVM निर्देशिका "com / acme / example" निर्देशिका में "Foon.class" को देखने जा रहा है:

  • यदि आपकी निर्देशिका संरचना उपरोक्त पैटर्न के अनुसार पैकेज नामकरण से मेल नहीं खाती है, तो JVM आपकी कक्षा नहीं ढूंढ पाएगा।

  • यदि आप इसे स्थानांतरित करके कक्षा का नाम बदलने का प्रयास करते हैं, तो यह भी असफल हो जाएगा ... लेकिन अपवाद स्टैकट्रैक अलग होगा।

एक ठोस उदाहरण देने के लिए, यह मानते हुए कि:

  • आप com.acme.example.Foon क्लास को चलाने के लिए चाहते हैं,
  • पूर्ण फ़ाइल पथ /usr/local/acme/classes/com/acme/example/Foon.class ,
  • आपकी वर्तमान कार्यशील निर्देशिका /usr/local/acme/classes/com/acme/example/ ,

फिर:

# wrong, FQN is needed
java Foon

# wrong, there is no `com/acme/example` folder in the current working directory
java com.acme.example.Foon

# wrong, similar to above
java -classpath . com.acme.example.Foon

# fine; relative classpath set
java -classpath ../../.. com.acme.example.Foon

# fine; absolute classpath set
java -classpath /usr/local/acme/classes com.acme.example.Foon

टिप्पणियाँ:

  • अधिकांश जावा रिलीज में -classpath विकल्प को -classpath छोटा किया जा सकता है। java , javac आदि के लिए संबंधित मैन्युअल प्रविष्टियों की जांच करें।
  • कक्षाओं में पूर्ण और सापेक्ष पथनामों के बीच चयन करते समय ध्यान से सोचें। याद रखें कि यदि मौजूदा निर्देशिका बदलती है तो एक सापेक्ष पथनाम "तोड़ सकता है"।

कारण # 2 सी - वर्गपथ से गायब निर्भरताएं

क्लासपाथ में अन्य सभी (गैर-सिस्टम) कक्षाएं शामिल करने की आवश्यकता है जिन पर आपका आवेदन निर्भर करता है। (सिस्टम कक्षाएं स्वचालित रूप से स्थित होती हैं, और आपको शायद ही कभी इसके साथ चिंता करने की आवश्यकता होती है।) मुख्य वर्ग को सही तरीके से लोड करने के लिए, JVM को खोजने की आवश्यकता है:

(नोट: जेएलएस और जेवीएम विनिर्देश कक्षाओं को "आलसी" वर्ग लोड करने के लिए एक जेवीएम के लिए कुछ गुंजाइश की अनुमति देते हैं, और जब क्लासलोडर अपवाद फेंक दिया जाता है तो यह प्रभावित हो सकता है।)

कारण # 3 - वर्ग को गलत पैकेज में घोषित किया गया है

कभी-कभी ऐसा होता है कि कोई व्यक्ति स्रोत कोड फ़ाइल को उनके स्रोत कोड पेड़ में गलत फ़ोल्डर में रखता है, या वे package घोषणा छोड़ देते हैं। यदि आप इसे आईडीई में करते हैं, तो आईडीई का कंपाइलर आपको इसके बारे में तुरंत बताएगा। इसी तरह यदि आप एक सभ्य जावा बिल्ड टूल का उपयोग करते हैं, तो उपकरण इस तरह से javac चलाएगा जिससे समस्या का पता चल जाएगा। हालांकि, अगर आप अपना जावा कोड हाथ से बनाते हैं, तो आप इसे इस तरह से कर सकते हैं कि कंपाइलर समस्या को नहीं देखता है, और परिणामी ".class" फ़ाइल उस स्थान पर नहीं है जहां आप उम्मीद करते हैं।

java -jar <jar file> वाक्यविन्यास

"निष्पादन योग्य" JAR फ़ाइलों के लिए उपयोग किया जाने वाला वैकल्पिक वाक्यविन्यास इस प्रकार है:

  java [ <option> ... ] -jar <jar-file-name> [<argument> ...]

जैसे

  java -Xmx100m -jar /usr/local/acme-example/listuser.jar fred

इस मामले में एंट्री-पॉइंट क्लास (यानी com.acme.example.ListUser ) और क्लासपाथ का नाम JAR फ़ाइल के मैनिफ़ेस्ट में निर्दिष्ट किया गया है।

IDEs

एक सामान्य जावा आईडीई में आईडीई जेवीएम में या बच्चे जेवीएम में जावा एप्लिकेशन चलाने के लिए समर्थन है। ये आम तौर पर इस विशेष अपवाद से प्रतिरक्षा होते हैं, क्योंकि आईडीई रनटाइम क्लासपाथ बनाने के लिए अपने स्वयं के तंत्र का उपयोग करता है, मुख्य वर्ग की पहचान करता है और java कमांड लाइन बनाता है।

हालांकि यह अपवाद होने के लिए अभी भी संभव है, यदि आप आईडीई के पीछे चीजें करते हैं। उदाहरण के लिए, यदि आपने पहले अपने जावा ऐप के लिए एक्लिप्स में एक एप्लिकेशन लॉन्चर स्थापित किया है, और फिर आपने ग्रहण को बताए बिना फ़ाइल सिस्टम में "मुख्य" कक्षा को एक अलग स्थान पर जेएआर फ़ाइल को स्थानांतरित कर दिया है, तो ग्रहण अनजाने में JVM लॉन्च करेगा गलत वर्गपथ के साथ।

संक्षेप में, यदि आपको यह समस्या किसी आईडीई में मिलती है, तो स्टेल आईडीई स्थिति, टूटी हुई परियोजना संदर्भ या टूटी हुई लॉन्चर कॉन्फ़िगरेशन जैसी चीज़ों की जांच करें।

आईडीई के लिए भ्रमित होने के लिए भी संभव है। आईडीई सॉफ़्टवेयर के बेहद जटिल टुकड़े हैं जिनमें कई इंटरैक्टिंग पार्ट्स शामिल हैं। आईडीईई को पूरी तरह उत्तरदायी बनाने के लिए इन भागों में से कई विभिन्न कैशिंग रणनीतियों को अपनाते हैं। ये कभी-कभी गलत हो सकते हैं, और एप्लिकेशन लॉन्च करते समय एक संभावित लक्षण समस्याएं होती हैं। अगर आपको संदेह हो रहा है कि यह हो रहा है, तो यह आपके आईडीई को पुनरारंभ करने लायक है।

अन्य संदर्भ


इस आदेश का प्रयोग करें:

java -cp . [PACKAGE.]CLASSNAME

उदाहरण: यदि आपका क्लासनाम हैलो.जावा हैलो.जावा से बनाया गया है तो नीचे दिए गए कमांड का उपयोग करें:

java -cp . Hello

अगर आपकी फ़ाइल Hello.java पैकेज com.demo के अंदर है तो नीचे दिए गए कमांड का उपयोग करें

java -cp . com.demo.Hello

जेडीके 8 के साथ कई बार ऐसा होता है कि कक्षा फ़ाइल एक ही फ़ोल्डर में मौजूद है, लेकिन java कमांड क्लासपाथ की अपेक्षा करता है और इस कारण से हम -cp . जोड़ते हैं -cp . क्लासपाथ के संदर्भ के रूप में वर्तमान फ़ोल्डर को लेने के लिए।


कभी-कभी समस्या के कारण मुख्य वर्ग के साथ कुछ भी नहीं हो सकता है, और मुझे इसे कठिन तरीके से ढूंढना पड़ा। यह एक संदर्भित पुस्तकालय था जिसे मैंने स्थानांतरित किया, और उसने मुझे यह दिया:

मुख्य वर्ग xxx लिनक्स को नहीं मिला या लोड नहीं किया जा सका

मैंने अभी उस संदर्भ को हटा दिया है, इसे फिर से जोड़ा है, और यह फिर से ठीक काम करता है।


कोशिश करें -Xdiag

स्टीव सी के जवाब में संभावित मामलों को अच्छी तरह से शामिल किया गया है, लेकिन कभी-कभी यह निर्धारित करने के लिए कि वर्ग नहीं मिला या लोड किया जा सकता है, यह इतना आसान नहीं हो सकता है। java -Xdiag ( java -Xdiag 7 के बाद से) का प्रयोग करें। यह एक अच्छा स्टैकट्रैक प्रिंट करता है जो संदेश को Could not find or load main class संदेश का अर्थ Could not find or load main class इसका संकेत प्रदान करता है।

उदाहरण के लिए, यह आपको मुख्य कक्षा द्वारा उपयोग की जाने वाली अन्य कक्षाओं को इंगित कर सकता है जो मुख्य वर्ग को लोड नहीं किया जा सका और रोका नहीं जा सका।


त्रुटि संदेश के अनुसार ("मुख्य वर्ग नहीं मिला या लोड नहीं किया जा सका"), समस्याओं की दो श्रेणियां हैं:

  1. मुख्य वर्ग नहीं मिला
  2. मुख्य वर्ग लोड नहीं किया जा सका (इस मामले को स्वीकार किए गए उत्तर में पूरी तरह से चर्चा नहीं की गई है)

मुख्य श्रेणी पूरी तरह से योग्य वर्ग नाम में टाइपो या गलत वाक्यविन्यास नहीं होने पर पाया जा सकता है या यह प्रदान किए गए क्लासपाथ में मौजूद नहीं है

कक्षा को शुरू नहीं किया जा सकता है जब मुख्य वर्ग लोड नहीं किया जा सकता है , आम तौर पर मुख्य वर्ग एक और वर्ग का विस्तार करता है और वह कक्षा प्रदान की गई कक्षा में मौजूद नहीं है।

उदाहरण के लिए:

public class YourMain extends org.apache.camel.spring.Main

यदि ऊंट-वसंत शामिल नहीं है, तो इस त्रुटि की सूचना दी जाएगी।


पहले इस आदेश का उपयोग कर पथ सेट करें;

set path="paste the set path address"

फिर आपको कार्यक्रम लोड करने की जरूरत है। संग्रहीत ड्राइव में "cd (फ़ोल्डर नाम)" टाइप करें और इसे संकलित करें। उदाहरण के लिए, यदि मेरा प्रोग्राम डी ड्राइव पर संग्रहीत है, तो "डी:" टाइप करें और "cd (फ़ोल्डर नाम)" टाइप करें।


मुझे कमांड लाइन पर क्लासपाथ निर्दिष्ट करने में क्या मदद मिली, उदाहरण के लिए:

  1. नया फ़ोल्डर बनाएं, C:\temp

  2. C:\temp में फ़ाइल Temp.java बनाएं, इसमें निम्न श्रेणी के साथ:

    public class Temp {
        public static void main(String args[]) {
            System.out.println(args[0]);
        }
    }
    
  3. फ़ोल्डर C:\temp में कमांड लाइन खोलें, और Temp क्लास को संकलित करने के लिए निम्न आदेश लिखें:

    javac Temp.java
    
  4. संकलित जावा क्लास चलाएं, -classpath को यह -classpath लिए -classpath विकल्प जोड़ना है कि कक्षा कहां खोजें:

    java -classpath C:\temp Temp Hello!
    

मेरे मामले में समस्या क्या तय हुई थी:

उस प्रोजेक्ट / क्लास पर राइट क्लिक करें जिसे आप चलाने के लिए चाहते हैं, फिर Run As -> Run Configurations । फिर आपको या तो अपनी मौजूदा कॉन्फ़िगरेशन को ठीक करना चाहिए या निम्न तरीके से नया जोड़ना चाहिए:

Classpath टैब खोलें, Advanced... बटन पर क्लिक करें, फिर अपनी प्रोजेक्ट के bin फ़ोल्डर जोड़ें।


मैंने इस समस्या को हल करने की कोशिश कर एक सभ्य समय बिताया। मैंने सोचा कि मैं किसी भी तरह से अपने क्लासपाथ को गलत तरीके से स्थापित कर रहा था लेकिन समस्या यह थी कि मैंने टाइप किया था:

java -cp C:/java/MyClasses C:/java/MyClasses/utilities/myapp/Cool  

के बजाय:

java -cp C:/java/MyClasses utilities/myapp/Cool   

मैंने सोचा कि पूरी तरह से योग्यता का अर्थ पूर्ण पैकेज नाम के बजाय पूर्ण पथ नाम शामिल करना था।


यदि आप जेएआर फ़ाइल बनाने के लिए Maven का उपयोग करते हैं, तो कृपया pom.xml फ़ाइल में मुख्य श्रेणी निर्दिष्ट करना सुनिश्चित करें:

<build>
    <plugins>
        <plugin>
            <artifactId>maven-jar-plugin</artifactId>
            <configuration>
                <archive>
                    <manifest>
                        <mainClass>class name us.com.test.abc.MyMainClass</mainClass>
                    </manifest>
                </archive>
            </configuration>
        </plugin>
    </plugins>
</build>

यदि आपकी कक्षाएं संकुल में हैं तो आपको मुख्य निर्देशिका में cd करना होगा और कक्षा के पूर्ण नाम (packageName.MainClassName) का उपयोग करना होगा।

उदाहरण:

मेरी कक्षाएं यहां हैं:

D:\project\com\cse\

मेरी मुख्य कक्षा का पूरा नाम है:

com.cse.Main

तो मैं मुख्य निर्देशिका में वापस cd :

D:\project

फिर java कमांड जारी करें:

java com.cse.Main

यदि आपकी मुख्य विधि किसी पैकेज के अंतर्गत कक्षा में है, तो आपको इसे पदानुक्रमित निर्देशिका में चलाया जाना चाहिए।

मान लें कि एक स्रोत कोड फ़ाइल (Main.java) है:

package com.test;

public class Main {

    public static void main(String[] args) {
        System.out.println("salam 2nya\n");
    }
}

इस कोड को चलाने के लिए, आपको निर्देशिका में ./com/test/Main.Java निर्देशिका में रखना चाहिए ./com/test/Main.Java । और रूट निर्देशिका में java com.test.Main उपयोग करें।


यह एक विशिष्ट मामला है, लेकिन जब से मैं इस पृष्ठ पर एक समाधान की तलाश में आया और उसे नहीं मिला, तो मैं इसे यहां जोड़ दूंगा।

विंडोज़ (7 के साथ परीक्षण) वर्ग और पैकेज नामों में विशेष पात्रों (जैसे) को स्वीकार नहीं करता है। हालांकि, लिनक्स करता है।

जब मैंने .jar में एक .jar बनाया और इसे कमांड लाइन में चलाने की कोशिश की तो मुझे यह पता चला। यह नेटबीन में भाग गया लेकिन कमांड लाइन में नहीं।


विंडोज़ पर डाल दिया .; शुरुआत में क्लास्स्पैट मूल्य पर।

द। (डॉट) का अर्थ है "वर्तमान निर्देशिका में देखें"। यह एक स्थायी समाधान है।

इसके अलावा आप सेट CLASSPATH=%CLASSPATH%;. साथ "एक बार" सेट कर सकते हैं CLASSPATH=%CLASSPATH%;. । यह तब तक टिकेगा जब तक आपकी सीएमडी विंडो खुली न हो।


All answers here are directed towards Windows users it seems. For Mac, the classpath separator is : , not ; । As an error setting the classpath using ; is not thrown then this can be a difficult to discover if coming from Windows to Mac.

Here is corresponding Mac command:

java -classpath ".:./lib/*" com.test.MyClass

Where in this example the package is com.test and a lib folder is also to be included on classpath.


I got this error after doing mvn eclipse:eclipse This messed up my .classpath file a little bit.

Had to change the lines in .classpath from

<classpathentry kind="src" path="src/main/java" including="**/*.java"/>
<classpathentry kind="src" path="src/main/resources" excluding="**/*.java"/>

सेवा मेरे

<classpathentry kind="src" path="src/main/java" output="target/classes" />
<classpathentry kind="src" path="src/main/resources" excluding="**"  output="target/classes" />

In Java, when you sometimes run the JVM from the command line using the java executable and are trying to start a program from a class file with public static void main (PSVM), you might run into the below error even though the classpath parameter to the JVM is accurate and the class file is present on the classpath:

Error: main class not found or loaded

This happens if the class file with PSVM could not be loaded. One possible reason for that is that the class may be implementing an interface or extending another class that is not on the classpath. Normally if a class is not on the classpath, the error thrown indicates as such. But, if the class in use is extended or implemented, java is unable to load the class itself.

Reference: https://www.computingnotes.net/java/error-main-class-not-found-or-loaded/


In my case, I got the error because I had mixed UPPER- and lower-case package names on a Windows 7 system. Changing the package names to all lower case resolved the issue. Note also that in this scenario, I got no error compiling the .java file into a .class file; it just wouldn't run from the same (sub-sub-sub-) directory.


Sometimes, in some online compilers that you might have tried you will get this error if you don't write public class [Classname] but just class [Classname] .


When running the java with the -cp option as advertised in Windows PowerShell you may get an error that looks something like:

The term `ClassName` is not recognized as the name of a cmdlet, function, script ...

In order to for PowerShell to accept the command, the arguments of the -cp option must be contained in quotes as in:

java -cp 'someDependency.jar;.' ClassName

Forming the command this way should allow Java process the classpath arguments correctly.





main