黑马程序员技术交流社区

标题: 局部变量 [打印本页]

作者: 1312564637    时间: 2015-10-14 12:15
标题: 局部变量
局部变量用的时候必须给他初始值,可为什么有的局部变量只定义不给他初始化也没事,有的就会报错呢

作者: 徐慧shanghai    时间: 2015-10-14 12:37
不知道你具体指的是哪些??
有些可能是有默认值的,譬如int 类型默认为0   等
有些没有初始值  例如 String   或者一些class 类这样的直接使用就会出现空指针异常,所以会需要你给一下初始值
作者: 徐慧shanghai    时间: 2015-10-14 13:11
徐慧shanghai 发表于 2015-10-14 12:37
不知道你具体指的是哪些??
有些可能是有默认值的,譬如int 类型默认为0   等
有些没有初始值  例如 Strin ...

                int a;
                if(a>100){
                       
                }
               
                int b;
                b=10;

譬如这样的两种写法
第一种会抱错,
因为你这个a 其实没有对他进行赋值,就对他进行判断,那虽然语法上不错,但是却是完全没有意义的,因为a 的值都没有给过就直接要使用,这样java认为不对
                int a;
                a=100;
                if(a>100){
                       
                }
这样写它就认为对了,至少你使用过一次a的值

至于b 这样直接赋值而不是使用b的值,它认为是没有问题的

觉得好难解释

作者: 1312564637    时间: 2015-10-14 14:28
public static void main(String[] args) {
                //isZhi(13);
                isZhi(96);
        }
        //此函数可判断传入的数是否为质数
    public static void isZhi(int a){
            Boolean flg=true;
           
            for(int i=2;i<a-1;i++){
                    if((a%i)==0){
                            flg=false;
                            break;
                    }                       
            }
这段代码如果你光给flg定义不赋值,就出错
作者: 1312564637    时间: 2015-10-14 14:30
public static void main(String[] args) throws IOException {
       FileInputStream fi=new FileInputStream("E:\\exam");
       ByteOutputStream b=new ByteOutputStream();
       int len;
      
       while((len=fi.read())!=-1){
               b.write(len);
       }
       System.out.println(b);
        }
而这段代码的len 你给他赋值还是不赋值都不会出错, 只有是局部变量,我一般都会给他赋值,肯定不会出错
作者: 1312564637    时间: 2015-10-14 14:50
上面的代码可能输出的结果不正确,因为传的是字节,中间需写的时候需转换一下

        private static void io() throws FileNotFoundException, IOException {
                FileInputStream fi=new FileInputStream("a.txt");
                   int b=8;
                   while((b=fi.read())!=-1){
                           System.out.println((char)b);
                   }
                                  
                   fi.close();
        }给你这段代码,其中的b,你付任何值,结果都不会变,因为后面又重新给他赋值了,而且你不赋值也没事
作者: primeget    时间: 2015-10-14 15:23
1312564637 发表于 2015-10-14 14:50
上面的代码可能输出的结果不正确,因为传的是字节,中间需写的时候需转换一下

        private static void io()  ...

你说的这些情况不是说没有赋值,你可以去看看,8种基本数据类型其实它都是有默认值的,而报错的那些变量,都是非基本数据类型的,像你上面提到的Boolean类型,是8种基本类型的boolean类型的对象类型,如果你把那个变量换成boolean的话,就不会报错了,这种情况报的错都是空指针异常,你可以用下面的代码查看到8种基本数据类型的默认值
int  num;
System.out.println(num);
打印他的值,你会看到他们都是有默认值的
Boolean bool;
System.out.println(bool);
打印这个对象它是会输出NULL
当你在操作一个空对象的时候,他是会报异常的。
作者: 1312564637    时间: 2015-10-14 15:28
上面没赋值,可底下不是又给他符了值了吗,管他呢,反正局部变量给他赋上值肯定没错
作者: primeget    时间: 2015-10-14 15:38
1312564637 发表于 2015-10-14 15:28
上面没赋值,可底下不是又给他符了值了吗,管他呢,反正局部变量给他赋上值肯定没错 ...

public static void main(String[] args) {
                //isZhi(13);
                isZhi(96);
        }
        //此函数可判断传入的数是否为质数
    public static void isZhi(int a){
            Boolean flg=true;
           
            for(int i=2;i<a-1;i++){
                    if((a%i)==0){
                            flg=false;
                            break;
                    }                       
            }
这段代码如果你光给flg定义不赋值,就出错

这个地方,刚开始没赋值,下面运行的代码也必须是a%i==0的时候才会给他赋值,如果一但没有进入这个条件,其实flg还是没赋值的,没赋值flg=null,操作null的时候就会异常
作者: 1312564637    时间: 2015-10-14 15:44
public static void isZhi(int a){
            Boolean flg=true;
           
            for(int i=2;i<a-1;i++){
                    if((a%i)==0){
                            flg=false;
                            break;
                    }                       
            }
            if(flg)
                    System.out.println("您输入的是质数");
            else
                    System.out.println("您输入的不是质数");
    }
}
代码没有粘贴权,, flg是判读他是否是质数的一个标识符
作者: FTD    时间: 2015-10-14 21:47
因为在内存中,你可能会分配到没有垃圾值得区域,但是当你分配到其他程序或者你自己的遗留下来的垃圾值得时候,就会用那个啦.当时初始化的时候九不会有这些不必要的麻烦啦.(就好像你去一个宿舍住宿,原来的人可能会留下一些垃圾在你宿舍,也有可能是一处没有被住过的~~)
作者: VV烽火    时间: 2015-10-14 22:24
本帖最后由 VV烽火 于 2015-10-14 22:55 编辑
1312564637 发表于 2015-10-14 14:28
public static void main(String[] args) {
                //isZhi(13);
                isZhi(96);


这个位置你不给flg赋值肯定出错啊,不过如果你if下面还有else语句flg=true;上面就可以不给flg设置初始值,因为在编译的时候java虚拟机会检查赋值,if有判断条件没给它赋值,最终else会给他赋值,所以能编译过。
public static void isZhi(int a){
            Boolean flg;
            
            for(int i=2;i<a-1;i++){
                    if((a%i)==0){
                            flg=false;
                            break;
                    }      
                  else{
                   flg = true;
}
            }
作者: 田策    时间: 2015-10-14 23:13
如果不给初始值的话就要私有化前面要加Pirvate,如果还是报错的话你就扑捉一下异常用try      catc方法应该可以解决
作者: 田策    时间: 2015-10-14 23:18

如果不给初始值的话就要私有化前面要加Pirvate,如果还是报错的话你就扑捉一下异常用try      catc方法应该可以解决
作者: Ei_Ki_    时间: 2015-10-15 00:11
对于这样的题,你要了解它的作用域即可。
作者: chengaq0    时间: 2015-10-15 08:55
局部变量是指,方法内,也就是局部代码块内声明的变量,你说的没事的是不是成员变量啊
作者: 赖洪光    时间: 2015-10-15 10:48
定义在方法里或域里就叫做局部变量,所谓域就是{}里面,比如
public class Test {
private String name;//成员变量,也是全局变量
public void changeName() {
String n = "tomoya";//n就是局部变量
name = n;
}
}
作者: 雨来    时间: 2015-10-15 20:51
作用域是在方法中还是在类中你首先要明白 的
作者: hxl8945    时间: 2015-10-15 22:19
引用类型 都会自动赋初始值的,一般用new 来创建对象的 都是会自动赋值的 比如 int[] arr = new int[5],,如果是在成员函数里面 比如你定义一个 int a;没有赋值 但不使用a 是不会报错的,一使用就会提示没有赋初始值
作者: 迷茫不堪的年纪    时间: 2015-10-16 02:22
总结以上作用域的同时, 要清楚成员变量和局部变量的定义,存储的方式不同,作用范围也不用, 多数的局部类型数据不会报错,但是个别还是会报错的,例如之前有人说到null .
作者: Love1027    时间: 2015-10-16 07:28
定义局部变量时赋值这是一个好的编程习惯。假如定义局部变量时没有赋初值,那么在程序运行时编译器会给该局部变量重新分配空间,这样效率低下,并且浪费栈空间。
作者: 罗志辉    时间: 2015-10-16 12:43
  1. class  Demo6
  2. {
  3.         int x;//此处x属于成员变量(定义在类内),具有默认值0,可以直接使用,相当于int x=0;
  4.         public static void main(String[] args)
  5.         {
  6.                 int y;//此处y属于局部变量(定义在方法内),虽然我并未给它赋值,但是如果我并没有使用它,那么编译就不会报错
  7.                 for(int z=0;1<5;z++)
  8.                 {
  9.                         y=4;
  10.                         //此句代码在编译之前,系统会先编译y=z,因为这两句在一个作用域里面,所以赋值了,编译不出错
  11.                         System.out.println(y);
  12.                         break;
  13.                 }
  14.                 /*报错,编译时是找语法错误,而之上的for语句需要被执行,才会有赋值,但是编译时是不会去执行代码的,所以虽然for循环的条件100%永久成立,但是在相同的作用域下,只有个for循环,并没有赋值语句。所以y没有被赋值,因此这句话会报错.如果在第6行时给y赋值2,那么此句不会报错,但是输出的结果是4,这是因为执行时,for循环中又重新赋值了*/
  15.                 System.out.println(y);
  16.         }//楼主,思考代码会不会报错,要站在编译器的角度思考,不要站在执行者的角度思考
  17. }
复制代码

作者: 吃饭工作睡觉    时间: 2015-10-16 15:54
1312564637 发表于 2015-10-14 14:30
public static void main(String[] args) throws IOException {
       FileInputStream fi=new FileInputS ...

这里面可定不会出错了。因为:while((len=fi.read())!= -1){
中len=fi.read()本身就是在为len赋值。如果说不太平常是因为这里是使用fi.read()的返回值为len赋值了。
作者: 帮助信息    时间: 2015-10-16 21:35
你首先得区分局部变量和成员变量
作者: liudongcan    时间: 2015-10-16 23:36
1312564637 发表于 2015-10-14 14:28
public static void main(String[] args) {
                //isZhi(13);
                isZhi(96);

局部变量变量是存储在栈内存,栈内存的变量都没有默认初始化值的。成员变量存储在堆内存,堆内存的变量都有默认初始化值,如String是null int 类型是0。有的局部变量能用因为是引用类型,存储在堆内存。比如数组,数组存储在堆内存,元素有默认初始化值
作者: 15555566103    时间: 2015-10-16 23:41
你仔细看看,确定是局部变量吗?确定变量在方法里吗?
作者: 15555566103    时间: 2015-10-16 23:43
局部变量不许定义个方法里  或者方法声名上(就是当作参数传递)  先把概念高清楚
作者: 15555566103    时间: 2015-10-16 23:46
第一个叫做声明变量,  第二个叫做定义变量
作者: qq739617099    时间: 2015-10-17 00:41
那当然是有的是默认了,系统在进行读取的时候会自动给他赋值,就比如int的默认值就是0,不过还是最好带上初始值,养成一个好习惯嘛,,,,,学姐把分给我吧,新人需要啊!!!
作者: 土豆丝    时间: 2015-10-17 22:56
请理解成员变和局部变量之间的区别
作者: 斑点狗    时间: 2015-10-18 10:22
我觉得有的不赋初值没事,有的会报错。这首先应该说下局部变量都在在哪些地方存在,在方法后面的形参中、在方法内定义的变量。这时方法后面的形参中的变量可以不用赋初值,因为在调用的时候就会给他赋值了。但在方法内定义的变量,这时要赋初值,不然会报错。
作者: 王子墨    时间: 2015-10-18 11:40
局部变量你不赋值的话,不引用它就没事,一用它就会报错。所以使用前还得赋值一次,可以先在上面定义,比如int a;  然后下面要想用a的话,就再输入 a = 10; 就行了。其它类型的都可参考这种方法
作者: tf0612    时间: 2015-10-20 10:42
在定义局部变量的代码块内,定义时没有给初始值,但是后面的语句给它赋值了,也 不会报错,例如:int a;
作者: wx_xO9vSwPo    时间: 2015-10-20 23:45
可能跟你用的编译器有关吧
作者: iq513394    时间: 2015-10-21 19:40
首先,你要理解,什么叫使用变量,是不是只要代码中出现了该变量就是使用了变量?我觉得不是。
我认为这“要先初始化才能使用”中的使用是指获取(get)变量的值。而其中的“初始化”就是设置(set)变量的值。
不管定义变量在哪里,有没有给初始化值,只要在获取(get)变量的值之前设置(set)了变量的值,就不会报错。
作者: cchjywall    时间: 2015-10-22 18:53
1312564637 发表于 2015-10-14 14:28
public static void main(String[] args) {
                //isZhi(13);
                isZhi(96);

你的boolean是封装类型的 返回值是null
作者: cchjywall    时间: 2015-10-22 19:02
局部变量在声明和首次提及的时候是无需赋值的,当首次被调用的时候才会去甄别是否已有。
作者: 孤单背影    时间: 2015-10-23 11:13
局部变量在使用的时候是必须先赋值再使用
作者: 北极的男娃    时间: 2015-10-27 21:54
只要你在用这个变量之前给他赋过初始值就行
你能不能给我举个具体的例子  不然我不好说
作者: 月明    时间: 2015-10-29 01:03
1312564637 发表于 2015-10-14 14:30
public static void main(String[] args) throws IOException {
       FileInputStream fi=new FileInputS ...

局部里的变量赋值可以分两步来做的 如果要用的时候就必须初始化 这里在while方法里使用 fi.read();给它赋了值 所以这里已经被初始化了 然后再看它是否等于-1  所以是在使用前已经被赋值
作者: 上帝的寵兒    时间: 2015-10-29 19:01
如果不给局部变量初始值程序也不会报错,但前提是不能参与运算,参与运算就会报错。这和成员变量不同,成员变量有默认的初始值,但局部变量没有!!!!新人入学,急需黑马币!!!
作者: Change.+    时间: 2015-10-29 19:11
如果不自动初始化,
可以让初始化的选择给用户,做到最少的初始化动作。
而用户不进行初始化的话,意味着用户不关心,但是明显,显示初始化是更好的习惯。
让用户写出来的话,更显得程序的某种完整性(能看出来初始化成什么样,而不是依赖
于是编译器偷偷摸摸在后面做手脚)
所以一方面可以认为可以在速度上,最少初始化,另一方面自由度交给了用户。
当然,自动进行初始化也是完全可以的,只要你习惯了在这里省点事,如果不动作,就让
编译器给一个默认动作。
作者: LOVE毛豆豆    时间: 2015-10-29 20:28
变量定义必须给初始值,但是如果你定义的时候不给,后面给也可以。如果后面也不给直接用就会报错。你的那个代码我看了,变量b你在判断的时候给它赋值了。跪求选择为答案。缺黑马币啊,不然不能上就业班。在这谢谢了
作者: redsifei    时间: 2015-10-30 23:13
局部变量使用前必须初始化
作者: 陈威    时间: 2015-10-31 23:31
你只需要记住只要在栈内存中的变量都不会初始化,在堆中和方法区中的都会初始化值!
作者: hnthgys    时间: 2015-11-5 15:48
定义局部变量时必须初始化。
当你定义一个局部变量,没有初始化变量,也没有使用这个变量时就不会报错,反之则报错。
作者: 帮助信息    时间: 2015-11-9 23:40
qishi有的时候真是搞不明白JVM在后台到底是怎么搞得 ,就跟一个静态刚发样不是说得用类名或者对象调用吗。但是子类调用父类的静态方法时,不用父类类名.调用或者是对象调用,直接用方法名就可以了。。
作者: chenxianzai    时间: 2015-11-10 20:04
final修饰的变量只能赋值一次,不会默认初始化,就会报错啦
作者: zhauibuzhai    时间: 2015-11-15 23:52
因为你程序里没用到它 只是放在那,  在用它前必须赋值,不然就报错了
作者: 袁有福123    时间: 2015-11-19 21:42
有些没给初始值是因为他默认有值  像Int的默认值为0  String的默认值为null  
作者: 袁有福123    时间: 2015-11-19 21:43
有些没给初始值是因为他默认有值  像Int的默认值为0  String的默认值为null  
作者: zhuwenjia    时间: 2015-11-22 16:25
这个可不可能与编译器有关系,默认是需要付初值的。
作者: 隔壁马良    时间: 2015-11-23 00:29
Boolean的值只能是true或者false,你不给初始赋值的话它也蒙啊




欢迎光临 黑马程序员技术交流社区 (http://bbs.itheima.com/) 黑马程序员IT技术论坛 X3.2