Java中的变量与变量的作用域
关于Java中的变量及变量的作用域
关于Java中的变量及变量的作用域
0. 变量的概念
在程序运行期间,系统可以为程序分配一块内存单元,用来存储各种类型的数据。系统分配的内存单元要使用一个标记符来标识,这种内存单元中的数据是可以更改的。所有叫变量。定义变量的标记符就是变量名,内存单元中所装载的数据就是变量值。用一个变量定义一块内存以后,程序就可以用变量名代表这块内存中的数据。根据所存储数据类型的不同,有各种不同类型的变量。
1. Java的变量类型
2. 注意变量的有效取值范围
系统为不同的变量类型分配不同的空间大小,如double型常量在内存中占8个字节,float的变量占4个字节,byte型占1个字节等。
byte b=129;//编译报错,129超出了byte类型的取值范围
float f=3.5;//编译报错,因为小数常量的默认类型为double型。double型在内存中占8个字节,而Java只为float的变量分配4个字节的空间,显然有问题
float f=3.5f;//编译通过
3. 基本数据类型之间的转换
①.自动类型转换(隐式类型转换)
要实现自动类型转换,需要同时满足两个条件:i.两种类型彼此兼容,ii.目标类型的取值范围要大于源类型。
byte b=3;
int x=b;//程序把b的结果自动转换成int型
②.强制类型转换(显式类型转换)
当两种类型彼此不兼容,或目标类型取值范围小于源类型时,自动转换无法进行,就需要强制类型转换。
byte a;
int b;
a=(byte)b;
将int型的变量b的取值强制转换成byte型,再将该值赋给变量a。此时,变量b本身的数据类型并没有改变。
例:
程序清单:Conversion.java
public class Conversion
{
public static void main(String[] args)
{
byte b;
int i=266;
b=(byte)i;
System.out.println("byte to int is"+" "+b);
}
}
程序输出如下:
byte to int is 10
十进制266→二进制100001010
byte类型取值范围为-128~127,所以只能取到010,省略0,所以输出10
也就是用目标内存块去套取源内存中的数据,能套多少算多少
4. 表达式的数据类型自动提升
下面来看一个错误程序:
程序清单:Test.java
class Test
{
public static void main(String[] args)
{
byte b=5;
b=(b-2);
System.out.println(b);
}
}
这段代码中,5-2的值并未超出byte型取值范围,然而却报错
这是因为在表达式求值时,变量值被自动提升为int型,表达式结果也就成了int型,这时想把它赋给byte型变量就必须强制转换了。
因此就应该改成:
b=(byte)(b-2);
关于类型的自动提升,Java定义了若干适用于表达式的类型提升规则
- 所有byte型、short型和char型的值奖杯提升为int型
- 如果一个操作数为long型,计算结果就是long型
- 如果一个操作数为float型,计算结果就是float型
- 如果一个操作数为double型,计算结果就是double型
也就是byte、short、char→int→long→float→double
下面演示一些Java的类型自动提升规则:
程序清单:Promote.java
class Promote
{
public static void main(String[] args)
{
byte b=50;
char c='a';
short s=1024;
int i=50000;
float f=5.67f;
double d=.1234;
double result=(f*b)+(i/c)-(d*s);
System.out.println((f*b)+"+"+(i/c)+"-"+(d*s));
System.out.println("result="+result);
}
}
下面看看代码行的类型提升:
double result=(f*b)+(i/c)-(d*s);
在第一个子表达式f*b中,变量b被提升为float类型,该子表达式的结果也被提升为float类型。接下来,在子表达i/c中,变量c被提升为int类型。该子表达的结果提升为int类型。
然后子表达式d*s中的变量s被提升为double类型,该子表达式的结果提升为double类型。
最后这三个结果值类型分别为float、int、double。float类型加int类型的结果是float类型,然后float类型减去double类型,该表达式的最后结果就是double类型。
变量的作用域
大多数程序设计语言都提供了“变量作用域”(Scope)的概念。在C、C++、Java中,一对大括号中间部分就是一个代码块,代码块决定其中定义的变量的作用域。代码块由若干语句组成,必须用大括号括起来,形成一个复合语句,多个复合语句可以潜逃在另外的一对大括号中形成更复杂的复合语句。
{
int x=0;
{
int y=0;
y=y+1;
}
x=x+1;
}
代码块决定了变量的作用域,作用域决定了变量的“可见性”以及“存在时间”。
例如:
程序清单:TestScope.java
public class TestScope
{
public static void main(String[] args)
{
int x=12;
{
int q=96;//x和q都可用
System.out.println("x is "+x);
System.out.println("q is "+q);
}
q=x;/*错误的行,只有x可用,q超出作用域范围*/
System.out.println("x is "+x);
}
}
q作为在里层的代码块中定义的一个变量,只有在那个代码块中位于这个变量定义之后的语句,才可以使用这个变量,q=x语句已经超过了q的作用域,所以编译无法通过。
在定义变量的语句所属的那层大括号之间,就是这个变量的有效作用范围,但是不能违背变量先定义后使用的原则。
6. 局部变量的初始化
在一个函数或函数里面的代码块中定义的变量称为局部变量,局部变量在函数或代码块被执行时创建,在函数或代码块结束时被摧毁。局部变量在进行取值操作前必须被初始化或进行过赋值操作,否则会出现编译错误。例如:
程序清单:TestVar.java
public class TestVar
{
public static void main(String[] args)
{
int x;//应改为int x=0;
x=x+1;//这个x由于没有初始化,编译报错
System.out.println("x is "+x);
}
}
Java中的变量与变量的作用域的更多相关文章
- JAVA中局部变量 和 成员变量有哪些区别
JAVA中局部变量 和 成员变量有哪些区别 1.定义的位置不一样<重点>***局部变量:在方法的内部成员变量:在方法的外部,直接写在类当中 2.作用范围不一样<重点>***局部 ...
- Java 中(静态)变量、(静态)代码块的执行顺序
Java 中(静态)变量.(静态)代码块的执行顺序 非原创 本文讨论 Java 中(静态)变量.(静态)代码块的执行顺序 首先创建 3 个类 1.Foo 类 public class Foo { pu ...
- 在 Java 中不使用多余变量交换两个字符串
在 Java 中不使用多余变量交换两个字符串 public class Test { public static void main(String[] args) { String a = " ...
- 关于java中jdk的环境变量配置
关于java中jdk的环境变量配置 烦死人,在网上找了很长时间.最终找到了一个方法!现在将其总结帮助后来人. 方法/步骤 1 下载好jdk,并按照提示一步步安装,最后记下jdk所在的安装位置,这里 ...
- Java中private、protected和public作用域的异同
Java中private.protected和public作用域的异同 说明:(1)private的作用范围为当前类,protected的作用范围哦不能超过其他包: (2)区别不同的作用域的不同作用范 ...
- 理解Java中的对象,变量和方法
1.对象的创建和销毁 1.1 对象的创建 这里只介绍创建对象与构造方法的关系 (1).每实例化一个对象就会自动调用一次构造方法,实质上这个过程就是创建对象的过程,准确的说,在Java语言中使用new操 ...
- Java基础知识强化10:Java中的中间缓存变量机制
1.对于自增运算++j与j++,由于加一的执行顺序不同,所以Java中有中间缓存变量来储存其单个表达式的值,而j的自增自减的结果依然保留在原来的变量储存区.因为本体是j的值,而单个表达式的值是中间产生 ...
- Java中实例方法,实例变量,静态方法,静态变量,final方法重写的问题,覆盖
Java中只有非私有的实例方法能被重写,即实现多态,子类可以覆盖父类的方法,但是实例变量不能覆盖,若子类和父类均定义了同样名称的变量,则对于子类来说这是两个不同的变量,要想调用父类的变量必须显示去调用 ...
- Java入门以及Java中的常量与变量总结
JDK与JRE的区别: JDK给开发人员使用(包含开发工具),JRE给客户使用(运行java程序的核心类库),JDK包含JRE关键字的含义: JAVA语言赋予特殊含义,具有专门用途的单词,关键字的单词 ...
- Java中final关键字修饰变量、方法、类的含义是什么
Java中的关键字final修饰变量.方法.类分别表示什么含义? 先看一个简单的介绍 修饰对象 解释说明 备注 类 无子类,不可以被继承,更不可能被重写. final类中的方法默认是final的 方法 ...
随机推荐
- javaScript 工作必知(十) call apply bind
call 每个func 都会继承call apply等方法. function print(mesage) { console.log(mesage); return mesage; } print ...
- C语言处理CSV文件的方法(一)
什么是CSV文件 CSV是 Comma-separated values (逗号分隔值)的首字母缩写,它通常是以逗号且不仅限于逗号分隔各个值,我们都叫他CSV. 看下面的例子: China, Shan ...
- nginx代理配置
server { listen 80; server_name api.colortrip.cn; client_max_body_size 10m; a ...
- Viewing the Raw SQL Statement(xcode で)
Thanks to Core Data. Even without learning SQL and database, you’re able to perform create, select, ...
- PHP判断图片是否存在和jquery中load事件对图片的处理
在公司的图片服务器中,同一个产品一般会存在对应的大图和缩略图.因此,我们在开发手机端的web网站时,默认使用的是产品图片的缩略图,查询数据库时获取的是缩略图的路径.但是,不知什么原因,时不时的,测试的 ...
- codeforces 652E . Pursuit For Artifacts 强连通分量
题目链接 题目大意: 给一个图, n个点m条边, 某些边上面有权值. 一条边只能走一次, 给两个点s, t. 问你, 从s到t能否经过有权值的边. 首先肯定要缩点, 然后看同一个连通分量里面的边, 是 ...
- 第6章 堆排序,d叉堆,优先队列
#include<stdio.h> #include<stdlib.h> #include<string.h> #define leftChild(i) (2*(i ...
- ADO.NET入门
什么是ADO.NET ADO.NET就是一组类库,这组类库可以让我们通过程序的方式访问数据库,就像System.IO下的类用类操作文件一样, System.Data.这组类是用来操作数据库(不光是MS ...
- Sql Server数据库快照初探
什么是快照 数据库快照是 SQL Server 数据库(源数据库)的只读静态视图.换句话说,快照可以理解为一个只读的数据库.利用快照,可以提供如下好处: 提供了一个静态的视图来为报表提供服务 可以利用 ...
- 【每天一个Linux命令】12. Linux中which命令的用法
which 用来查看可执行文件的位置. 1.命令格式: which 可执行文件名称 2.命令功能: which指令会在PATH变量指定的路径中,搜索某个系统命令的位置,并且返回第一个搜索结果. 3. ...