2011-04-13 14 views
18

के भीतर एक्सेस किया गया है, मुझे अपना कोड संकलित करने के बाद दो त्रुटियां मिलीं।स्थानीय चर को आंतरिक वर्ग (जावा)

त्रुटियाँ हैं:

:

1.

local variable input is accessed within inner class; 
    needs to be declared final 
    String name = input.getText(); 

2.

local variable c_age is accessed within inner class; 
    needs to be declared final 
    Object child_age = c_age.getSelectedItem(); 

यह मेरा कोड है

import javax.swing.*; import java.awt.event.*; public class GUI { public static void main(String[] args) { JFrame frame = new JFrame("Try GUI"); JLabel l1 = new JLabel("Please Enter Your Child's Name"); JTextField input = new JTextField("",10); JLabel l2 = new JLabel("Choose Your Child's Age"); String[] age = {"Age","1","2","3","4","5","6"}; JComboBox c_age = new JComboBox(age); JButton button = new JButton("Search"); JTextArea result = new JTextArea(); JScrollPane extend_area = new JScrollPane(result); button.addActionListener(new ActionListener() { public void actionPerformed(ActionEvent ae) { String name = input.getText(); Object child_age = c_age.getSelectedItem(); } }); JPanel panel = new JPanel(); panel.add(l1); panel.add(input); panel.add(l2); panel.add(c_age); panel.add(button); panel.add(extend_area); frame.add(panel); frame.setSize(350,350); frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); frame.setVisible(true); } } 

मैं इस त्रुटि को कैसे हल कर सकता हूं?

उत्तर

16

आप

JTextField input = new JTextField("",10); 

और

JComboBox c_age = new JComboBox(age); 

इस तरह की घोषणा करने की जरूरत है:

final JTextField input = new JTextField("",10); 

final JComboBox c_age = new JComboBox(age); 

इसका मतलब है कि input और c_age नहीं बदल सकते:

और c_age:

स्पष्टीकरण जावा भाषा विशिष्टता से लिया, Section - 8.1.3 Inner Classes and Enclosing Instances

+0

समस्या हल हो गई। लेकिन मैं आपकी व्याख्या को समझ नहीं पा रहा हूं। आप और अधिक दे सकते हैं ... बहुत बहुत धन्यवाद एडवर्ड – Roubie

+0

जावा भाषा विशिष्टता के लिए एक अंश और लिंक संलग्न, मुझे उम्मीद है कि मदद करता है ... – edwardsmatt

+3

अंतिम की आवश्यकता है ताकि उपयोगकर्ता जब वे आंतरिक कक्षा/बंद द्वारा उपयोग किया जा रहा है चर परिवर्तक नहीं बदल सकता है। इसके बारे में सोचें: यदि इसे अंतिम के रूप में चिह्नित नहीं किया गया है, तो आंतरिक कक्षा संदर्भ घोषणा के बगल में कुछ भी कोड कर सकते हैं, इसलिए आपको इसे समवर्ती समस्याओं से बचने के लिए अंतिम रूप में चिह्नित करना होगा, और सिंटैक्स इसे लागू करता है। –

0

जेटीक्स्टफिल्ड नाम का नाम मुख्य विधि के अंदर घोषित किया गया था। आपको शायद ऐसा कुछ करना चाहिए:

public class GUI{ 

     //declare all your components here e.g. 

     JTextField input; 

     public static void main(String args[]){ 
       new GUI(); 
     } 

     public GUI(){ 
      //instantiate components here 
      input = new JTextField(); 
      //and so on. 
     } 

    } 

इस तरह आंतरिक कक्षा के अंदर इनपुट के संदर्भ में कोई समस्या नहीं होगी।

+0

मुझे यह त्रुटि है: गैर स्थैतिक चर को स्थिर संदर्भ – Roubie

+0

से संदर्भित नहीं किया जा सकता है मुख्य विधि स्थिर संदर्भ है। आपको अपने उदाहरण की तरह अपनी कक्षा के उदाहरण को तुरंत चालू करके इसे तोड़ना होगा। आपके मुख्य विधि से विभिन्न कोड कन्स्ट्रक्टर में जाना चाहिए। –

0

आप final दो चर आप में जाकर कर रहे हैं की घोषणा करने के लिए है।

यदि आप ऐसा नहीं करना चाहते हैं, तो आप या तो एक नया उचित वर्ग (विज्ञापन-प्रसार नहीं) बना सकते हैं और उन्हें कन्स्ट्रक्टर में पैरामीटर के रूप में पास कर सकते हैं, या (मैंने ऐसा किया जब जीयूआई के साथ काम करते हुए जावा) एक श्रोता वर्ग बनाएं जो अपने कन्स्ट्रक्टर में ऑब्जेक्ट लेता है और उन्हें स्थानीय रूप से उपलब्ध कराता है, फिर विज्ञापन-प्रसार तुरंत चालू करें।

2

आपके आंतरिक वर्ग के actionPerformed विधि के अंदर उपयोग किए जाने वाले किसी भी चर को अंतिम घोषित करने की आवश्यकता होगी। निम्न का प्रयास करें:

import javax.swing.*; 
import java.awt.event.*; 

    public class GUI 
    { 
     public static void main(String[] args) 
     { 
      JFrame frame = new JFrame("Try GUI"); 
      JLabel l1 = new JLabel("Please Enter Your Child's Name"); 
      final JTextField input = new JTextField("",10); 

      JLabel l2 = new JLabel("Choose Your Child's Age"); 
      String[] age = {"Age","1","2","3","4","5","6"}; 
      final JComboBox c_age = new JComboBox(age); 

      JButton button = new JButton("Search"); 

      JTextArea result = new JTextArea(); 
      JScrollPane extend_area = new JScrollPane(result); 

      button.addActionListener(new ActionListener() 
      { 
        public void actionPerformed(ActionEvent ae) 
        { 
         String name = input.getText(); 
         Object child_age = c_age.getSelectedItem(); 


        } 
      }); 

      JPanel panel = new JPanel(); 
      panel.add(l1); 
      panel.add(input); 
      panel.add(l2); 
      panel.add(c_age); 
      panel.add(button); 
      panel.add(extend_area); 
      frame.add(panel); 
      frame.setSize(350,350); 
      frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 
      frame.setVisible(true); 
     } 

    } 
+0

क्या आप समझा सकते हैं कि इसे अंतिम घोषित करने की आवश्यकता क्यों है? – Seth

0

विधि निष्पादन पूर्ण होने के बाद इनपुट चर और c_age चर गायब हो जाता है। स्थानीय आंतरिक कक्षाओं के अंदर इन चरों का उपयोग करने की अनुमति नहीं दी जाएगी जब तक कि यह अंतिम न हो।

5

If you declare the variables as an final then it will solve your errors but according to me its not the good solution for the problem. Similar problem has discussed here you can have a look here for more understanding.

In solution to yours problem you can have define methods by using them you can get better solution. For hint you can read How to access non-final local variable inside anonymous inner class

+0

दूसरी तरफ आप अपने इनपुट और c_age चर को स्थिर आवृत्ति चर के रूप में घोषित कर सकते हैं जो आपकी समस्या का समाधान करेगा। –

0

मैंने अभी मुख्य वर्ग जैसे 'tempString' में एक अस्थायी var बनाया है और फिर इसे समस्या के कारण होने वाले var पर सेट किया जा सकता है।तो:

tempString = myString 

इस तरह से मैं बिना किसी समस्या के tempString को कॉल कर सकता हूं। नीचे मेरी उदाहरण की जाँच करें:

// Create my temp var here 
private String tempUrl; 

// my function here 
public void updatePage(String url) 
{ 
    // Can use 'url' here because it's not within inner class 
    if(!url.equals("")) 
    { 
     // Set 'tempUrl' to 'url' so I can use it without problem 
     tempUrl = url; 

     // My inner class that used to cause the problem 
     backgroundUpdate = new Thread(new Runnable() 
     { 
      // From here on I use 'tempUrl' to solve the problem 
      public void run() 
      { 
       // Do something with 'tempUrl' here (where 'url' used to be used) 
      } 
     }); 

     backgroundUpdate.start(); 
    } 
} 
1

जोड़ने final लचीलापन का एक बहुत दूर ले जाता है, मैं निम्नलिखित सुझाव देना चाहते हैं: एक्सेसर विधि है, जो वैसे भी प्रोत्साहित किया जाता है पैदा करते हैं। लेकिन ऑब्जेक्ट्स से निपटने पर यह ज्यादातर उपयोगी होता है, जबकि आपके मामले में सबकुछ स्थिर होता है। इसलिए, यह उत्तर आपकी विशिष्ट स्थिति पर लागू नहीं हो सकता है, लेकिन क्योंकि आपके त्रुटि संदेश के लिए गुगलिंग इस सवाल को शीर्ष परिणाम के रूप में उत्पन्न करता है, मुझे लगता है कि अधिकांश मामलों में लागू एक विकल्प (ऑब्जेक्ट्स का उपयोग करना एक स्थिर विधि से सबकुछ करने से अधिक आम है) यहां भी उपस्थित होना चाहिए।

public class MyClass extends MySuperClass { 
    private MyPropertyClass aProperty; 

    public MyClass() { 
     new JButton().setActionListener(new ActionListener() { 
      public void actionPerformed(ActionEvent e) { 
       // aProperty.aMethod(); -- Bang! That should be final, the compiler says. 
       getMyProperty().aMethod(); // -- Everything okay, works fine, no compiler complaints. 
      } 
     }); 
    } 

    public getMyProperty() { 
     return aProperty; 
    } 
} 
संबंधित मुद्दे