当前位置: 代码迷 >> J2SE >> 小弟我的一小段程序,一运行就空指针异常,为什么
  详细解决方案

小弟我的一小段程序,一运行就空指针异常,为什么

热度:6155   发布时间:2013-02-25 00:00:00.0
我的一小段程序,一运行就空指针错误,为什么
我模仿网上的多线程不同写了一个自动提款机的小程序,一运行就扔空指针错误。我eclipse提示是Thread.start()方法错误了,可是我看不出这里怎么就空指针了,我明明创建了对象啊。
Java code
public class my{    public static void main(String[] args){        ATM[] pArr=new ATM[100];        for(int i=0;i<pArr.length;++i){            pArr[i].start();        }    }    static class Account{        int m_amount;        String m_name;        Account(int m,String name){            m_amount=m;            m_name  =name;        }        void Deposit(int m){            try{                int a=m_amount;                a+=m;                Thread.sleep(100);                m_amount=a;            }catch(InterruptedException e){                e.printStackTrace();            }        }        void WithDraw(int m){            try{                int a=m_amount;                a-=m;                Thread.sleep(100);                m_amount=a;            }catch(InterruptedException e){                e.printStackTrace();            }        }    }    static class ATM extends Thread{        static Account m_acc=new RevertList.Account(10,"self");        public void run(){            m_acc.Deposit(1);            m_acc.WithDraw(1);        }    }}


------解决方案--------------------------------------------------------
创建了数组,数组里的对象默认是null,需要初始化!
------解决方案--------------------------------------------------------
如果是基本类型的数组的话,系统会分配一个默认初始值,比如int数组就是0
但如果是引用类型的话,分配了内存但没有初始化,即null,因而提示空指针异常
------解决方案--------------------------------------------------------
对象数组为空
可以再for循环里创建多个线程

------解决方案--------------------------------------------------------
初学者常见错误:

你只是创建了数组,但没有创建数组中的元素:
for(int i=0;i<pArr.length;++i){
pArr[i] = new ATM(); // 这才真的创建了数组中的元素所引用的对象。
pArr[i].start();
}

------解决方案--------------------------------------------------------
探讨

初学者常见错误:

你只是创建了数组,但没有创建数组中的元素:
for(int i=0;i<pArr.length;++i){
pArr[i] = new ATM(); // 这才真的创建了数组中的元素所引用的对象。
pArr[i].start();
}

------解决方案--------------------------------------------------------
ATM[] pArr=new ATM[100];
你只是创建了数组,但没有创建数组中的元素所以是个长度为100的空数组
------解决方案--------------------------------------------------------
ATM[] pArr=new ATM[]{new ATM()};
------解决方案--------------------------------------------------------
探讨
引用:

引用:
如何又能指定大小,又能在创建数组的时候指定new ATM()呢?


不行的。按照我 4 楼的做法来吧。


我按照你的说法来做了,不过发现,每次运行的结果都是"正确的"。这很奇怪,按照网上的说法,这个程序我既然没有对Deposit和Withdraw来加锁,那么应该运行的结果不确定才对啊。

------解决方案--------------------------------------------------------
探讨

初学者常见错误:

你只是创建了数组,但没有创建数组中的元素:
for(int i=0;i<pArr.length;++i){
pArr[i] = new ATM(); // 这才真的创建了数组中的元素所引用的对象。
pArr[i].start();
}

------解决方案--------------------------------------------------------
与其在这里告诉LZ是什么引起了空指针异常,还不如告诉LZ怎么用Debug调试。你这次知道原因了,下次一粗心,不会又来这里发个帖子吧。
Debug断点到发生错误的地方,然后看变量,(x)=Variables窗口你调试的时候看过多少次?出了问题就一头裁进代码里看,睁大了眼睛,自信满满的以为看一眼就能知道哪里出错,总有一天你会感觉到头昏脑胀的。
------解决方案--------------------------------------------------------
关于第10楼----
难道你认为'Final amount=10'的结果是正确的? 它可以是这样的情况
1. 所有ATM的线程都还没跑到run里面(毕竟需要时间),就输出了
2. 所有ATM的线程都还没跑到给m_amount赋值那里,就输出了
3. 有一个ATM的线程'刚好'跑完一个run而其它线程处于1 或 2的情况,就输出了.
---
要重现错误,只要在Debug下控制不同线程在run里一步一步跑上去就很容易看到了.
------解决方案--------------------------------------------------------
  相关解决方案