JAVA入门基础(2)


第 2 章  变量
一个 Java 程序是由许多类和对象组成的,而类和对象又是由字段(通常用变量代表)和方法(通常
用函数代表)等组成的。这一章,我们将学习什么是变量,在 Java 程序中为变量命名需要遵循什么样的
规则,以及如何使用变量。
2.1   标识符和关键字
在编写 Java 应用程序时,经常需要为程序、类、对象、方法和变量等命名,这就需要了解 Java 语
言中的“标识符”和“关键字”的概念,以及标识符的命名规则。
2.1.1   标识符
Java 语言中,用来标识类名、对象名、变量名、方法名、类型名、数组名、文件名的有效字符序列,
称为“标识符”。简单地说,标识符就是一个名字。
Java 语言规定,标识符由字母、数字、下画线和美元符号组成,并且第一个字符不能是数字。例如,
下列标识符都是合法的。
Dog    class_3    _price   $123   $23boy
下列标识符为非法的。
3_class    No.1    ¥123
说明:Java 语言是区分大小写的,所以标识符 boy 与 Boy 是不同的。
当然了,我们为标识符命名时,也可以取中文名称,如“价格”、“数量”、“孙悟空”等。不过
按惯例,我们通常取英文的名称(毕竟在中英文输入法间切换也是相对麻烦的事)。
2.1.2   关键字
在 Java 语言中,还有一些专门的词汇, Java 语言使用它们来代表特定的含义。所以程序员在编写程
序时, 就不能再使用这些词汇来命名标识符,不能改变这些词汇的含义。这些专有词汇,称为“关键字”。
例如在社会生活中,“公安局”这个词已经被赋予了特定的含义,所以如果有人开个商店,他绝对
不能给商店取名为“公安局”。在这里,“公安局”就是社会生活中的关键字。那么,在 Java 语言中同
样如此。对于有特定含义的关键字,在编程时不能用来命名自定义的标识符。
Java 的关键字对 java 的编译器有特殊的意义,是 Java 语言中为语法定义的需要而特别定义的标识
符。这些标识符构成了 Java 语言最基本的语素,它们用来表示一种数据类型,或者表示程序的结构等。
如表 2.1 中列出了 Java 语言的所有关键字。
表 2.1   Java语言关键字列表
abstract  boolean  break  byte  case  catch  char  class 
2
const  continue  default  do  double  else  enum  extends
final  finally  float  for  goto  if  implements  import
instanceof  int  interface  long  native  new  package  private
protected  public  return  short  static  strictfp  super  switch
synchronized  this  throw  throws  transient  try  try  void
volatile  while           
说明:true、false、null 不是关键字,它们称为“保留字”,但是仍然不能使用它们命名标识符。所
谓“保留字”, 是指为 Java 预留的关键字,它们虽然现在没有作为关键字,但在以后的升级版本中有可
能作为关键字。
2.1.3   标识符命名规则
为了提高程序的可读性,在程序中定义标识符时,要尽量遵循“望文生义”的原则,即名称要能代
表变量本身的含义。例如定义一个标识符代表价格,那么取名为“price”,就会让其他人看到这个标识
符就能明白它代表价格。
Java 标识符的具体命名规则如下。
  一个标识符可以由几个单词连接而成,以表明它所代表的含义,如 applePrice。这也称为“驼峰
命名法”。
  如果是类名,每个单词的首字母都要大写,其他字母则小写,如 StudentInfo。
  如果是方法名或者变量名,第一个单词的首字母小写,其他单词的首字母都要大写,如方法
getStudentInfo()、变量 studentName。
  如果是常量,所有单词的所有字母全部大写,如果由多个单词组成,通常情况下单词之间用下
画线“_”分隔,如 PI、MAX_VALUE。
  如果是包名,所有单词的所有字母全部小写,如 examples.chapter02。
2.2   常量与变量
在编写程序时,经常接触到不同类型的数据。有的数据在程序运行期间是不允许改变的,如数学运
算中的圆周率π;有的数据在程序运行期间是需要经常改变的,如价格、数量等。这就需要在程序中有
相应的表示。
2.2.1   常量的概念及常量声明
常量是指在程序执行期间其值不能发生变化的数据。常量是固定的,其值在程序运行期间是不能改
变的。如整数 123,小数 1.23,字符’A’,布尔常量 true、false 等。
在 Java 中,常量分为字面常量和符号常量两种。
  字面常量:指的是如 123、12.34、‘m’、true 这样字面上本身就是一个固定值的数据。
  符号常量:指的是代表一个固定值的标识符。
2.2.1.1  字面常量
字面量指的是代表一个固定值的原代码。字面量在程序代码中直接显示,不要求进行计算。Java 中
的字面量有整数字面量、浮点数字面量、字符字面量和字符串字面量。 
·3·
(1)整数字面量
如果一个整数字面量以字母“L”或“l”结尾,其数据类型为 long;否则,其数据类型为 int。因为
使用小写字母 l 容易与数字 1 混淆,所以建议使用大写字母 L。
整数字面量可以由三种数字系统表示:
  十进制:基于 10,其数字由 0 到 9 组成。这是我们日常经常使用的数字系统。
  十六进制:基于 16,其数字由 0 到 9 以及字母 A 到 F 组成。
  二进制:基于 2,其数字由 0 和 1 组成。(从 Java SE 7 开始,可以创建二进制字面量)
在一般的编程中,我们最经常使用的可能只是十进制。不过,如果需要使用其它的数字系统,则可
以在程序中使用如下所示的语法:
int decVal = 42;      //十进制数 42
int hexVal = 0x2a;    //十六进制表示,表示数 42
int binVal = 0b0101010;  //二进制表示,表示数 42(JDK 7 开始增加的新特性)
(2)浮点数字面量
如果一个浮点数字面量以字母“F”或“f”结尾,其数据类型为 float;否则,其数据类型为 double
(可以显式地以字母“D”或“d”结尾)。
浮点类型(float 和 double)还可以使用 E 或 e 的表达形式(科学计数法)。下面是浮点数字面量的
使用语法:
double floatPointVal_1 = 123.4;
double floatPointVal_2 = 1.234e2;    //同样的值,以科学计数法表示
float floatPointVal_3 = 123.4f;
(3)字符和字符串字面量
字符字面量和字符串字面量可以包含任何 Unicode(UTF-16)字符。如果编辑器和文件系统允许,
我们可以直接在我们的代码中使用这样的字符。如果不允许的话,我们可以使用“Unicode 转义字符”,
如'\u0108'。字符字面量使用单引号括起来的单个字符,如'a',而字符串字面量使用双引号括起来的多个
字符序列,如"hello"。
(3)class 字面量
Java 中还有一个特殊类型的字面量,叫做“class 字面量”。其格式为一个类的名称后跟一个.class
后缀。例如,String.class。这个字面量指向代表该类型本身的对象(类型为 Class)。
2.2.1.2  符号常量
使用符号常量需要在程序中先声明后使用。所谓声明一个常量,指的是创建一个常量,为它起一个
名字,并指明它所代表的数据类型。
要声明一个符号常量,就必须使用关键字 final。声明符号常量的语法如下。
final  常量类型  常量标识符=常量值;
在声明常量时,通常情况下立即为其赋值,即立即对常量进行初始化。例如:
final float PI = 3.14F;                //声明一个 float 类型常量,并初始化为 3.14
final int STUENT_NUMBER = 24;          //声明一个整型常量,并初始化为 24
在声明常量标识符时,按照 Java 的命名规则,所有的字符都要大写。如果常量标识符由多个单词组
成,则在各个单词之间用下画线“_”分隔,如上例中的 STUENT_NUMBER。
在上面所示的例子中,是在声明符号常量时就进行初始化的。也可以分为两步,先声明常量,再进
行初始化,例如:
final float PI;                  //声明一个 float 类型常量
final int STUENT_NUMBER;            //声明一个整型常量
PI = 3.14F;                  //初始化为 3.14 
4
STUENT_NUMBER = 24;              //初始化为 24
但是初始化以后,就不允许再在程序中对这些常量进行重新赋值,即不允许改变常量的值。例如:
final int STUENT_NUMBER = 24;  //声明一个整型常量,并初始化为 24
STUENT_NUMBER = 32;      //企图修改常量 STUENT_NUMBER 的值,程序将报错
如果需要声明多个同一类型的常量,可以使用下面的语法:
final  常量类型  常量标识符 1,常量标识符 2,常量标识符 3,…;
final  常量类型  常量标识符 1=常量值 1,常量标识符 2=常量值 2,常量标识符 3=常量值 3;
例如:
final float PI,PRICE,WEIGHT;          //声明三个 float 类型的变量
final float PI=3.14F,price=13.86F,WEIGHT=86.32F;      //声明三个 float 类型的变量,同时进行初始化
2.2.2   变量的概念及变量声明
所谓变量,就是值在程序运行期间可以被改变的量。实际上,变量是程序在运行时内存中能够存储
数据的空间,变量的值可以在程序的任何地方被动态地改变。所以在编写程序时,经常需要声明变量,
向系统申请存储数据的内存空间。
Java 编程语言是“静态调用类型”的,这意味着所有的变量在使用之前必须先声明,即“先声明,
后使用”。要声明变量,就必须先创建它并为它取一个名字,并且指明它能够存储数据的类型,这称为
“变量声明”。如下所示:
int number = 1;
这个变量声明告诉程序存在一个名为“number”的字段,能保存整数,并且初始值为 1。
要在程序中声明一个变量,其语法形式如下。
变量类型  变量标识符;
变量类型类型会在下一节详细讲述。变量名称遵循标识符命名规则,并且第一个单词的首字母小写,
其它单词的首字母大写,其他字母一律小写。例如:
String studentName;              //声明一个 String 类型的变量,用来存放学生的姓名
int studentAge;                //声明一个 int 型变量,用来存放学生的年龄
在声明变量时,可以立即为其赋值,即立即对变量进行初始化,例如:
String studentName = “张小明”;          //声明一个 String 类型的变量,并初始化
int studentAge = 18;              //声明一个 int 型变量,并初始化
也可以先声明变量,然后在需要的时候再初始化,例如:
String studentName;              //声明一个 String 类型的变量
int studentAge;                //声明一个 int 型变量
studentName=”张小明”;            //初始化赋值
studentAge=18;              //初始化赋值
也可以同时声明多个同一类型的变量,如:
String studentName , teacherName;        //声明两个 String 类型的变量
String studentName=”张小明” , teacherName=”王金柱”;//声明两个 String 型变量,并初始化
变量与常量不同。变量的值如果需要的话,可以在程序的任何地方被改变。例如,下面的代码是正
确的。
String studentName = “张小明”;          //声明一个 String 类型的变量,并赋初值”张小明”
studentName = “李芳”;            //改变变量 studentName 的值为”李芳” 
·5·
2.3   原始数据类型
在现实生活中,有各种各样的数据类型,例如价格为 19.8 元(小数)、员工人数 25 人(整数)等。
而程序中的变量和常量,在处理具体业务时,将用来存储要处理的业务数据,所以,在声明变量时,必
须指明它能够存储数据的类型,也就是说,要指明变量的数据类型。
不同的数据类型,在内存中分配的空间大小也不一样。 原始数据类型是 Java 语言内置的专门的数据
类型,是构造语言的最基础的要素。本节将重点介绍 Java 语言中的各种原始数据类型。
2.3.1   数据类型
作为程序,处理的对象就是各种类型的数据。因此,程序设计语言中数据类型的多少,是衡量语言
功能是否强大的标准之一。 Java 语言有着非常丰富的数据类型,可分为原始数据类型和构造数据类型两
大类,如图 2.1 所示。
数据类型
原始数据类型
构造数据类型
整数类型
浮点类型
字符类型(char)
逻辑类型(Boolean)
数组

对象
接口
字节类型(byte)
短整型(short)
整型(int)
长整型(long)
单精度型(float)
双精度型(double)
图 2.1   Java 中的数据类型分类
原始数据类型是 Java 语言本身预先定义的、通过关键字命名的数据类型。 在 Java 语言中,一共有 8
个原始数据类型,可分为以下 4 种,分别为:
  整数类型;
  浮点类型;
  字符类型;
  逻辑类型
后面各节将分别对这几种原始(基本)数据类型进行详细的讲解和说明。
2.3.2   整数类型
整数类型的变量或常量,只能用来存放整数。例如,在某个程序中,要定义一个变量来保存员工的
人数,毫无疑问,人数必须是整数,不可能出现 0.6 个人这样的情况,所以定义这样的变量时,要将其
6
声明为整数类型。
在 Java 中,有四种整数类型,如表 2.2 所示。
表 2.2   Java中的整数类型
数据类型  关键字  分配内存大小  取值范围
字节型  byte  1个字节  -128~127(-2
7
~ 2
7
-1)
短整型  short  2个字节  -32768~32767(-2
15
~ 2
15
-1)
整型  int  4个字节  -2 147 483 648~2 147 483 647(-2
31
~ 2
31
-1)
长整型  long  8个字节  -9 223 372 036 854 775 808~-9 223 372 036 854 775 807 (-2
63
~ 2
63
-1)
所有这些类型都是有符号的,也就是说,它们的最高位代表的是正数或负数符号符号,所以它们既
能存储正数,也能存储负数。
不同类型的整型变量或常量,内存分配给它们的空间大小也不一样, 因此对于不同类型变量或常量,
它所能保存的数值的大小也是有限制的,不能超出它的取值范围。
正如在上节中讲的,程序员在程序中声明一个变量的时候,必须同时指明变量的数据类型,用以确
定这个变量可以保存值的范围。例如:
public class Example1{
public static void main(String[] args){
byte number1 = -128;        //声明一个字节型变量,并赋于初值-128
//byte number2 = -129;                  //错误。所赋的值超出了 byte 类型的取值范围下限
byte number3 = 127;          //声明一个字节型变量,并赋于初值 127
//byte number4 = 128;        //错误。所赋的值超出了 byte 型变量的取值范围上限
System.out.println("number1 = " + number1);
System.out.println(“number2 = ” + number2);
}
}
因为变量 number1、number2、number3 和 number4 声明为 byte 型的,它在内存空间中只被分配 1
个字节大小的空间,这 1 个字节所能容纳的数值的大小为-128  ~  127。所以为变量 number1 和 number3
赋的值是可以的,而为变量 number2 和 number4 所赋的值已经超出了 byte 类型所能容纳数值的范围,
编译时就会提示错误信息。
数据类型 int,通常是整数的默认数据类型。这个类型对于我们大多的程序来说,其大小足够使用了。
在大型的数组当中要节省内存的话,可以使用 byte 或 short。 不过如果需要更大范围的值,可以使用 long
型代替。
在为 long 型常量或变量赋值时,需要在所赋值的后面加上一个字母“L”(或小写“l”),说明所
赋的值为 long 型。如果所赋的值未超出 int 型的取值范围,也可以省略字母“L”(或小写“l”)。例
如,下面几种赋值方式都是正确的。
long account = 3124567893L;    //所赋的值超出了 int 型的取值范围,必须在后面加上字母“L”
long account = 31245678L;    //所赋的值未超出 int 型的取值范围,可以在后面加上字母“L”
long account = 31245678;      //所赋的值未超出 int 型的取值范围,可以省略字母“L”
但是下面的这种赋值方式是错误的。
long account = 3124567893;    //所赋的值超出了 int 型的取值范围,但是没有在后面加上字母“L”
注:上面示例中省略了字母“L”的数值 31245678,实际上就是字面常量,其默认数据类型为 int。
如果在其后面加上字母“L”,则其数据类型为 long 型。整数类型 byte、short、int 和 long 值可以由 int
字面量创建。超出了 int 类型值范围的 long 型值,可以从 long 型字面量创建。上面的示例中,将 int 型
的值 31245678 赋给 long 型的变量 account 时,会发生隐式数据类型转换,这在本章最后一节会详细讲
解。 
·7·
2.3.3   浮点类型
另一种能够存储数值的类型是浮点类型。声明为浮点类型的变量或常量,主要用来存储小数。
浮点类型包括两种:float 型(单精度 32 位 IEEE 754 浮点型)和 double 型(双精度 64 位 IEEE 754
浮点型),如表 2.3 所示。
表 2.3   Java中的浮点类型
数据类型  关键字  分配内存大小  取值范围
单精度型  float  4个字节  1.4E-45 ~ 3.4E+38
双精度型  double  8个字节  4.9E-324 ~ 1.797E+308
如果我们需要在一个保存浮点数值的大型数组中节省内存空间的话,建议使用 float 类型。不过需
要注意的是,对于精度要求高的值,如货币,则永远不要使用这个 类型 。 对于货币,要使用
java.math.BigDecimal 类代替(在后面的“数字和字符串处理”一章会详细讲解 BigDecimal 类以及其它
一些很有用的类)。
对于小数来说,通常默认使用 double 类型。同 float 一样,这个数据类型永远不要用于精度值,如
货币。
如果要声明一个用来保存小数的变量,必须将其声明为浮点类型。例如:
float price = 326.85F;        //声明一个 float 类型的变量,并赋值
double height = 3836.8;        //声明一个 double 类型的变量,并赋值
double height = 3836.8D;
如上面示例所示,在为 float 类型的变量赋值时,需要在所赋值的后面加上字母“F”或小写“f”,
否则编译时,会提示错误。因为不加上字母“F”或小写“f”时,默认的数据类型为 double 类型,而把
double 类型的数值赋给 float 类型的变量,是不正确的。
在为 double 类型的变量赋值时,既可以在所赋值的后面加上字母“D”或小写“d”,也可以不加。
浮点型变量除了可以接受小数之外,也可以接受整数,例如:
float price = 326;          //声明一个 float 类型的变量,并赋整数值
double height = 3836;        //声明一个 double 类型的变量,并赋整数值
如果所赋整数值的大小超出了 int 型的取值范围,那么也需要在所赋值的后面加上相应的字符“F
(f)”或“D(d)”,将其转换为小数,再赋值,例如:
float number = 2147483648;      //错误:所赋的整数值 2147483648 超出了 int 类型的取值范围
float price = 2147483648F;      //声明一个 float 类型的变量,并赋值
double height = 3836567893D;     //声明一个 double 类型的变量,并赋值
将整数赋值给 float 或 double 类型的变量时,会进行数据类型的转换,这在后面的“不同数据类型
之间的转换”一节中会有详细的说明。
2.3.4   字符类型
在程序中,还经常需要保存字母、数字符号、标点符号和其他符号等,如’a’、’#’、’3’,这就需要
用到另外一种数据类型——字符型。字符型变量或常量在内存中被分配 2 个字节的空间,用来存储单个
字符。
在 Java 语言中,使用关键字“char”来声明字符型常量或变量,例如:
char gender = „男‟;      //声明一个 char 类型的变量,用来存储性别信息
char star = „*‟;        //声明一个 char 类型的变量,用来存储符号‟*‟
final char PI = „π‟;      //声明一个 char 类型的常量,用来存储圆周率符号‟π‟ 
8
因为计算机只能识别二进制数据,所以在 Java 中,将不同的字符映射到不同的整数数字,再转换成
二进制的形式,以利于计算机对字符的识别。这种映射关系,就是“字符编码”。因为字符编码采用的
是将字符映射到整数数字的方法,所以字符也可以用整数来表示或参与数学运算。请看下面的例子:
public class Example2{
public static void main(String[] args){
int number = 'a';              //将 char 类型字面量值赋给 int 类型变量
System.out.println(number);    //输出结果为整数 97
char a = 97;                  //将 int 类型的字面量值赋给 char 类型变量
System.out.println(a);         //输出结果为字符'a'
int sum = 'a' + 3;             //字符可以和整数进行数学运算
System.out.println(sum);
char d = 'a' + 3;              //字符可以和整数进行数学运算
System.out.println(d);
}
}
编译并运行这个示例程序,输出结果如下:
97
a
100
d
在 Java 中,对字符采用 Unicode 编码。Unicode 使用 2 个字节表示 1 个字符,并且 Unicode 字符集
中的前 128 个字符与 ASCII 码字符集兼容。如字符‘a’,它的 ASCII 码的二进制数据表示形式为 01100001,
而它的 Unicode 码的二进制数据表示形式为 00000000 01100001,它们都表示十进制数的 97。
Unicode 编码采用的是无符号编码,在内存中占 2 个字节共 16 位,一共可以存储 65536 个字符。所
以在 Java 语言中,几乎可以处理世界上所有国家的语言文字,这也是 Java 特别适合互联网程序开发的
一个特点。
当声明一个 char 类型的变量并为其赋值时,所赋的值必须为一个英文字母、一个符号或一个汉字,
并且要用英文状态下的单引号括起来,如‘男’、‘*’、‘π’等。
有些字符,不能通过键盘输入到程序中,如回车符、换行符等,这就需要使用 Java 中的转义字符常
量。这些转义字符常量用特定的字符,表示无法在键盘上输入的字符,如表 2.4 所示。
表 2.4   Java中的转义字符
转义字符  含义
\n  表示换行
\t  表示横向跳格,作用同Tab键
\b  表示退格
\r  表示回车
\f  表示走纸换页
\\  表示反斜杠字符
\’  表示单引号字符
\”  表示双引号字符 
·9·
\d  表示八进制字符
\xd  表示十六进制字符
\ud  表示Unicode字符
需要注意的是,转义字符虽然是反斜杠“\”和一个字符的组合,但在 Java 中,它代表一个字符,
如下面代码所示。
public class Example3{
public static void main(String[] args){     
final char changeLine = '\n';  //声明一个 char 类型的变量,用来存储转义字符‟\n‟,代表换行
System.out.println("我"+changeLine+"爱"+changeLine+"你");  //输出连接后的字符串
}
}
在上面的代码中,定义一个 char 类型的变量 changeLine,并赋予一个转义字符值’\n’,然后输出一
行信息。输出结果如下。可以看出,转义字符发挥了作用,每输出一个字就进行了换行。



2.3.5   逻辑类型
在 Java 程序中,要保存逻辑值 true (真)或 false (假),需要声明逻辑型的常量或变量。逻辑类型
又称布尔类型。声明逻辑类型常量或变量,需要使用关键字 boolean。如下面示例所示。
boolean flag = false;                  //声明一个 boolean 类型的变量,初始值为 false
flag = true;                    //改变 flag 变量的值为 true
布尔类型的变量或常量,只能接受 true 和 false 这两个逻辑值,不能向布尔类型的变量赋除 true 和
false 之外的其他值。
2.3.6   默认值
当声明一个变量时,并不总是一定要为其赋一个值。如果我们声明的变量是字段变量,但是没有初
始化,那么编译器会为其设置一个合理的默认值。下表总结了上述 8 种原始数据类型的默认值:
表 2.5   原始数据类型的默认值
数据类型  默认值(为字段时)
byte  0
short  0
int  0
long  0L
float  0.0f
double  0.0d
char  '\u0000'
boolean  false
String(或任何对象类型)  null
注:只有实例变量(字段)才有默认值。局部变量和方法参数变量没有默认值,编译器永远不会给
一个未初始化的局部变量赋予一个默认值。 所以对于声明的局部变量,必须先为其赋值以后,才能使用。
直接访问一个未初始化的局部变量将导致一个编译时错误。(实例变量、类变量、局部变量和方法参数
变量,在后面的章节会集中讲解和对比) 
10
2.3.7   JDK 7  新特性:二进制字面量常量值和在数值型字面量中使用下划线
从 JDK 7 开始,增加了二进制字面量常量值的特性。可以这样定义一个变量并赋予二进制字面量值:
int number = 0b1010;
从 Java SE 7 开始,在一个数值型字面量中的任何数字之间,可以出现任意多个下划线(_)。这个
特性可以让我们将数值型字面量分隔成一组组的数字,这样可以提高代码的阅读性。
举例来说,如果代码中包含有许多位的数,我们就可以使用下划线字符将数字分隔为三个一组,类
似于使用如逗号或空格作为分隔符。
下面的例子中演示了怎样在数值型字面量中使用下划线:
long creditCardNumber = 1234_5678_9012_3456L;
long socialSecurityNumber = 999_99_9999L;
float pi = 3.14_15F;
long hexBytes = 0xFF_EC_DE_5E;
long hexWords = 0xCAFE_BABE;
long maxLong = 0x7fff_ffff_ffff_ffffL;
byte nybbles = 0b0010_0101;
long bytes = 0b11010010_01101001_10010100_10010010;
需要注意的是,下划线只能位于数字中间。不能将下划线放在下面这些位置:
  在数字的开始位置或最后位置
  在浮点字面量中紧挨着小数点
  位于 F 或 f 后缀之前
  希望是数字字符串的地方
下面这些例子演示了数值型字面量中有效的和无效的下划线位置:
float pi1 = 3_.1415F;        //  无效的:不可以将下划线位于小数点前后
float pi2 = 3._1415F;        //  无效的:不可以将下划线位于小数点前后
long socialSecurityNumber1 = 999_99_9999_L;  //  无效的:不可以将下划线位于 L 后缀之前
int x1 = _52;          //  这是一个标识符,不是一个数值字面量
int x2 = 5_2;          // OK (十进制数字面量)
int x3 = 52_;          //  无效的:不可以将下划线位于字面量最后
int x4 = 5_______2;        // OK (十进制数字面量)
int x5 = 0_x52;          //  无效的:不可以将下划线位于 0x 基数后缀中间
int x6 = 0x_52;          //  无效的:不可以将下划线位于一个数字的开头
int x7 = 0x5_2;          // OK (十六进制字面量)
int x8 = 0x52_;          //  无效的:不可以将下划线位于一个数字的最后
2.3.8  不同数据类型间的转换
当把一种数据类型变量的值赋给另一种数据类型变量时,或者不同类型的数据或数据变量混合在一
起进行运算时,就会需要对数据类型进行相应的转换。这种情况在编写程序时经常遇到,例如下面这行
代码:
System.out.println(3.6+4+‟a‟);    //输出表达式 3.6+4+‟a‟的值
上面这个语句,输出表达式 3.6+4+'a'的值,那么输出结果是什么呢?这就需要掌握不同数据类型之
间进行转换的规则。
在 Java 中,不同数据类型之间的转换,分为两种情况:自动类型转换和强制类型转换。
1.自动类型转换 
·11·
在对变量进行赋值时,如果是将低级数据类型(相对取值范围较小的数据类型)的数据,赋给高级
数据类型(相对取值范围较大的数据类型)的变量,这时 Java 会自动完成从低级类型向高级类型的转换。
在原始数据类型中,除了 boolean 类型外,其他数据均可参与算术运算,它们数据类型从低到高的排列
顺序如图 2.2 所示。
char
byte short
int long float double
低 高
图 2.2   数据类型级别与取值范围
图 2.2 中列出了数据类型的大小关系,一个类型是否可以自动隐式转换为另一种类型,要看是否能
通过箭头到达。例如下面的代码,在进行赋值运算时:
float price = 36;                    //定义 float 类型的变量,并赋值
System.out.println(“price=”+price);            //输出 price 变量的值:price=36.0
可以看出,因为相对于 float 类型来说,整数 36 为 int 型,属于低级数据类型,所以 Java 自动将其
转换为 float 类型的 36.0,并赋值给 float 类型的变量 price。可以得出这样的结论:将低类型的数据赋给
高类型的变量时,Java 会自动将低类型的数据转换为高类型的数据,然后赋值。
在不同类型的数据进行混合运算时,分为两种情况:
  参与混合运算的,只有 byte、short 或 char 类型的数据。
这种情况下,Java 首先将 byte 或 short 或 char 类型转换为 int 类型,然后再参与运算,并且运算结
果也是 int 型的。例如:
public class Example4{
public static void main(String[] args){     
byte    byteVar = 68;            //声明一个 byte 类型的字节变量
short   shortVar = 873;            //声明一个 short 类型的整型变量
char   charVar = 'a';              //声明一个 char 类型的字符变量
int    value = byteVar + shortVar + charVar;
System.out.println("value = " + value);      //输出 value 的值:value = 1038
}
}
在上面的示例中,分别将变量 byteVar、shortVar、charVar 转换为 int 型,然后相加,相加结果为 int
型,并赋值给 int 变量 value。
  参与混合运算的,含有 int、long、float 或 double 型的数据。
这种情况下, Java 首先将所有低数据类型转换为表达式中数据类型最高的数据类型,然后再参与运
算,并且运算结果也是表达式中最高的数据类型。例如:
public class Example5{
public static void main(String[] args){     
byte   byteVar = 68;              //声明一个字节类型的变量
int     intVar = 873;              //声明一个 int 类型的变量
float   floatVar = 128.5F;            //声明一个 float 类型的变量
double   value = byteVar + intVar + floatVar;    //不同数据类型变量进行混合运算
System.out.println(“value =  ”  + value);      //输出 value 的值:value = 1069.5 
12
}
}
在上面的示例中对 value 值的计算,最高数据类型为 double (变量 value 的数据类型),所以三个变
量 byteVar、intVar、floatVar 在进行加法运算时,首先都被转换为 double 型,然后相加,相加结果也为
double 型,并赋值给 double 型变量 value。
2、强制类型转换
在对变量进行赋值时,如果是将高级数据类型的数据赋给低级数据类型的变量,这时 Java 不会自动
地完成类型的转换,而必须由程序员手工强制进行类型转换。例如,在进行赋值运算时:
int count = 36.5;                  //定义 int 类型的变量,并赋值 double 类型的 36.5
System.out.println(“count=”+count);   
上述代码在编译是会提示错误,因为将高级类型的数据 36.5 赋给了低级类型的变量 count。如果改
为下面这种形式:
int count = (int)36.5;                  //强制类型转换
System.out.println(“count=”+count);            //输出 count 变量的值:count=36
上面代码中,(int)显示为强制类型转换的语法,即在欲转换的数据或变量前面,用“(目的数据
类型)”的形式,强制转换为括号中的目的数据类型。另外,在上面的示例中也可以看到,在进行强制
类型转换时,进行了简单的截断而不是四舍五入(输出 36,而不是 37)。
同样,在不同类型的变量进行混合运算时,程序员也可以通过强制类型转换,让参与运算的变量改
变数据类型。例如:
public class Example6{
public static void main(String[] args){     
byte   byteVar = 68;              //声明一个字节类型的变量
int     intVar = 873;              //声明一个 int 类型的变量
float  floatVar = 128.5F;            //声明一个 float 类型的变量
int   value = byteVar + intVar +(int) floatVar;    //混合运算,对 floatVar 进行强制类型转换
System.out.println(“value =  ”  + value);      //输出 value 的值:value = 1069
}
}
在上面的程序中,将 byte 类型的变量 byteVar、int 类型的变更 intVar 和 float 类型的变量 floatVar
进行混合加法运算,并将结果赋给一个整型变量 value。其中 byte 类型低于 int 类型,所以变量 byteVar
会自动转换为 int 类型。而 float 类型高于 int 类型,所以需要强制类型转换,将其转换为 int 型。然后三
个 int 型值相加,将结果赋给 int 类型的变量 value。
2.4  字符串
除了原始数据类型,在 Java 中还提供了一个字符串类型 String。String 并不是原始数据类型,而是
一种引用类型。但是由于字符串处理非常重要,并且在程序处理中被频繁用到,所以 Java 语言将 String
类型作为原始数据类型一样使用。
请看下面使用字符中类型 String 的示例程序:
public class StringExample {
public static void main(String[] args){
String bookName = "Java 从初学到精通";  //声明 String 类型的变量 
·13·
String bookAuthor = "辛立伟";      //声明 String 类型的变量
System.out.println(bookName);
System.out.println(bookAuthor);
//  字符串可以通过“+”号连接起来
String bookInfo = "书名:" + bookName + ",  作者:" + bookAuthor;
System.out.println(bookInfo);        
}
}
从上面的代码中,可以看到,String 类型的使用就象原始数据类型一样,这样在程序代码中可以很
方便地处理字符串类型的数据。另外,在编程时,经常需要把各个字符串连接在一起,形成一个单独的
字符串,Java 也提供了“+”(加号)运算符的重载,可以简单地通过加号把几个字符串连接起来。请
看下面的示例:
public class StringPlusExample {
public static void main(String[] args){
int number1 = 3;
int number2 = 5;
boolean flag = true;
char gender = '男';
String webSiteName = "Java 自学网";
System.out.println(number1 + number2 + webSiteName);  //自左至右运算,先计算两个整数的和
System.out.println(number1 + webSiteName + number2);
System.out.println(webSiteName + number1 + number2);
System.out.println(webSiteName + flag + gender);
}
}
编译并运行,输出结果为:
8Java 自学网
3Java 自学网 5
Java 自学网 35
Java 自学网 true 男
可以看到,字符串可以和其他数据类型使用“+”(加号)进行混合运算,这时 String 类型的级别
最高,即其它数据类型要先转换成字符串,然后进行字符串连接。这称为“+”(加号)运算符重载。
但是其中有个例外:
System.out.println(number1 + number2 + webSiteName);
在这行代码中,输出的表达式“number1 + number2 + webSiteName”自左至右运算。由于前两个参
与“+”运算的是两个整数,所以先进行加法运算,得到结果 8,然后是 8 和字符串 webSiteName 的“+”
运算,这时因为参与运算的有字符串类型,其级别最高,所以数字先转换成字符串“8”,然后与
webSiteName 进行连接,所以最终运算结果为“8Java 自学网”。
当然,Java 的 String 类型功能非常强大,这里我们只初步了解其最基本的使用。在后面的章节,我
们会详细讲解 Java 中对字符串处理的技术。
14
2.5  数组
在前面的示例程序中,我们都是通过定义单个变量来存储数据,但是在实际应用中,通常有批量的
数据需要处理,例如,需要存储 5 个学生的数学成绩。当然,可以在程序中定义 5 个变量来存储 5 个学
生的数学成绩,这些成绩都是单精度浮点类型,使用如下代码。
float mathScore_1 = 73.5F;
float mathScore_2 = 82.0F;
float mathScore_3 = 95.0F;
float mathScore_4 = 63.0F;
float mathScore_5 = 75.5F;
但是再考虑另一个问题:现在程序需要存储 50 个学生的数学成绩,怎么办?当然可以在程序中定
义 50 个变量来存储,只不过显得笨拙而已。但是,如果程序需要存储 500 个学生的数学成绩呢?需要
存储 5000、50000 个学生的数学成绩呢?
很显然,在上述情况下,对于同一类型的批量数据,在程序中再通过定义单个的变量这种方式已经
不能解决存储大批量数据的问题了,因为它既不经济,也不实际。对于这种类型的问题, Java 提供了“数
组”这种构造数据类型来解决。
2.5.1   什么是数组
数组是一个容器对象,用来存储固定数量的具有相同数据类型的数据,可以使用共同的名字来引用
数组中存储的数据。数组可以存储任何类型的数据,包括原始数据类型和对象,但是一旦指定了数组的
类型之后,就只能用来存储指定类型的数据。
数组的长度在创建数组是确定,在创建以后,其长度就固定下来了。
数组提供了一种数据分组的便利方法。在数组中,每一项数据都经过编号,可以通过数组的下标(即
数据项在数组中的索引值,从 0 开始。例如,数组中第一项数据的下标为 0,第二项数据的下标为 1,
第 N 项数据的下标为 N-1)来方便地访问。如下图所示:
数组当中的每项数据称为“元素”,每个元素可以通过其数字索引被访问到。正如上图所示,索引
数值从 0 开始。比如第 9 个元素,可以在索引值 8 的位置访问到。
可以在程序中定义一个只能用来存储整数的整型数组,也可以定义一个只能用来存储小数的 float
类型的数组,或者一个只能用来存储字符串的 String 对象数组,甚至于一个只能用来存储某一类型数组
的数组。但是,不可以定义一个既能存储整数,又能存储小数或其他类型数据的数组。 
·15·
2.5.2   Java 语言中数组的特点
在不同的程序设计语言中,一般都提供有数组这种数据类型,功能和使用方法都很类似。不过 Java
语言中的数组有自己的几个特点:
  Java 中的数组,既能存储原始数据类型,又能存储对象类型。
  数组元素的个数称为数组的长度。数组长度一旦确定,就不能改变。
  数组元素的下标是从 0 开始的,即第一个元素的下标是 0。
  Java 不支持多维数组,但是可以创建数组的数组。
  Java 中将数组作为对象处理。数组对象含有成员变量 length,用来表示数组的长度。
在本章的后面的内容中,将对这些特点逐一作详细讲解。
2.5.3  使用数组
在下面的程序 ArrayExample.java 中,创建了一个整型数组,然后放入一些值,并且打印每个值到标
准输出中。
class ArrayDemo {
public static void main(String[] args) {
int[] anArray;          //  声明一个整型数组
anArray = new int[10];        //  为 10 个 int 类型整数分配内存空间
anArray[0] = 100;        //  初始化第一个元素
anArray[1] = 200;        //  初始化第二个元素
anArray[2] = 300;        //  依次初始化每个元素
anArray[3] = 400;
anArray[4] = 500;
anArray[5] = 600;
anArray[6] = 700;
anArray[7] = 800;
anArray[8] = 900;
anArray[9] = 1000;
System.out.println("在索引位置 0 处的元素为: " + anArray[0]);
System.out.println("在索引位置 1 处的元素为: " + anArray[1]);
System.out.println("在索引位置 2 处的元素为: " + anArray[2]);
System.out.println("在索引位置 3 处的元素为: " + anArray[3]);
System.out.println("在索引位置 4 处的元素为: " + anArray[4]);
System.out.println("在索引位置 5 处的元素为: " + anArray[5]);
System.out.println("在索引位置 6 处的元素为: " + anArray[6]);
System.out.println("在索引位置 7 处的元素为: " + anArray[7]);
System.out.println("在索引位置 8 处的元素为: " + anArray[8]);
System.out.println("在索引位置 9 处的元素为: " + anArray[9]);
}
}
编译并运行该示例程序,输出结果为: 
16
在索引位置 0 处的元素为: 100
在索引位置 1 处的元素为: 200
在索引位置 2 处的元素为: 300
在索引位置 3 处的元素为: 400
在索引位置 4 处的元素为: 500
在索引位置 5 处的元素为: 600
在索引位置 6 处的元素为: 700
在索引位置 7 处的元素为: 800
在索引位置 8 处的元素为: 900
在索引位置 9 处的元素为: 1000
2.5.3.1   声明一个指向数组的变量
在创建和使用数组过程中,首先要做的就是声明一个数组变量,来保存实际的数组。声明数组变量
的含义如同声明一个原始数据类型的变量,要指明数组的数据类型以及数组的名字。在上面的例子中,
使用下面这行代码声明一个 int 类型的数组:
int[] anArray;          //  声明一个整型数组
Java 中声明数组的语法如下。
数组类型[ ]  数组名字; 
数组类型  数组名字[ ]; 
这两种数组变量声明的方式在作用上是相同的,但通常建议采用第一种方式,它更符合数组变量的
原理,即在数组名字前面指定数组可以保存的数据类型,这里使用方括号“[]”来代表数组类型。数组
的名称任意,但要遵循 Java 的标识符命名规则。 与其它类型的变量一样,这样的变量声明并不实际地创
建一个数组,它只是简单地告诉编译器这个变量将持有一个指定类型的数组。
同样地,也可以声明其它类型的数组:
byte[] arrayOfByte;      //声明一个 byte 类型数组
short[] arrayOfShort;     //声明一个 short 类型的数组
long[] arrayOfLong;      //声明一个 long 类型的数组
float[] arrayOfFloat;      //声明一个 float 类型的数组
double[] arrayOfDouble;    //声明一个 double 类型的数组
boolean[] arrayOfBoolean;  //声明一个布尔类型的数组
char[] arrayOfChar;      //声明一个字符类型的数组
String[] arrayOfString;    //声明一个字符串类型的数组             
也可以使用第二种声明数组变量的方式,将方括号放在数组名后面:
int weeks[];         
boolean flag[];
float score[];
2.5.3.2   创建、初始化和访问数组
声明了数组变量之后,下一步就需要创建一个数组对象,并将其赋给所声明的数组变量。而创建数
组对象,实际上就是在内存中分配相应大小的存储空间给数组。有两种方式可以用来创建数组对象。
(1)使用 new 运算符
在 Java 中,数组是引用对象,所以可以使用 new 运算符来直接创建一个数组对象。在上面的示例
程序中,使用如下代码创建数组:
anArray = new int[10];        //创建一个大小为 7 的整型数组,分配 7 个整数的内存空间
使用 new 运算符来创建数组对象时,必须指定这个数组的大小。创建数组对象时,仅仅是在内存中
为数组变量分配指定大小的空间,并没有实际存储数据,这时数组的所有元素会被自动地赋予初值,其
中: 
·17·
  数字数组,初值是 0。
  布尔数组,初值是 false。
  字符数组,初值是‘\0’。
  对象数组,初值是 null。
通常我们需要显式地为数组元素赋初值。在上面的示例程序中,使用如下代码为数组的每个元素赋
值:
anArray[0] = 100;        //  初始化第一个元素
anArray[1] = 200;        //  初始化第二个元素
anArray[2] = 300;        //  依次初始化每个元素,等等
要访问(指的是读写)数组中每个元素,可以通过其索引值。在上面的示例程序中,使用如下代码
读取数组每个元素的值并打印在标准输出:
System.out.println("在索引位置 0 处的元素为: " + anArray[0]);
System.out.println("在索引位置 1 处的元素为: " + anArray[1]);
System.out.println("在索引位置 2 处的元素为: " + anArray[2]);
注意:数组的索引值是从 0 开始计算的。Java 会严格检查数组的边界,以防止引用超出数组范围的
值。 Java 运行时环境会检查数组索引值以确保所有的数组索引都在正确的范围之内。如果在程序中引用
了索引值超出数组范围的元素, Java 编译器就会显示一个“ArrayIndexOutOfBoundsException”错误提示。
(2)创建和初始化数组的简洁方式
也可以通过把数组元素值直接放在大括号中的办法来同时完成创建和初始化数组,这时将在内存中
分配与元素数量相适应的空间大小,并赋予指定的元素值,如下代码所示。
int[] anArray = {100, 200, 300,400, 500, 600, 700, 800, 900, 1000};
使用这种方法创建数组对象时,大括号里的元素类型必须与指定的数据类型一致,并且数组的大小
由大括号中包含的元素个数决定。请看下面这个示例。
public class Test2{
public static void main(String[ ] args){
int age[ ] = {18,23};            //定义一个整型数组,大小为 2,并赋值初始化
System.out.println(age[0]);          //输出数组 age 的第一个元素值
System.out.println(age[1]);          //输出数组 age 的第二个元素值
String names[ ] =    {“张小明”,”黄芳”,”赵秀丽”};  //定义一个字符串类型数组,大小为 3,并赋值初始化
System.out.println(names[0]);        //输出数组 names 的第一个元素值
System.out.println(names[1]);        //输出数组 names 的第二个元素值
System.out.println(names[2]);        //输出数组 names 的第三个元素值
}
}
在本示例中,创建数组对象时,直接初始化数组元素。输出结果为:
18
23
张小明
黄芳
赵秀丽
2.5.3.3   修改数组元素
数组的大小不可改变,但数组中的元素值是可以改变的。在声明一个数组变量和创建一个数组对象
以后,可以通过为数组中的元素赋值,来修改数组中任一元素的值。请看下面的代码。
public class Test3{
public static void main(String[ ] args){ 
18
int mathScore[ ] = {78,93,84};          //定义一个整型数组,保存三个同学的数学成绩
int englishScore[ ] = new int[3];          //定义一个整型数组,保存三个同学的英语成绩
int totalScore[ ] = new int[3];          //定义一个数组,用来保存三个同学的总成绩
String[ ] students = {“张小明”,”黄芳”,”赵秀丽”};
//为三个同学的英语成绩赋值
englishScore[0] = 98;              //为第一个元素赋值
englishScore[1] = 72;              //为第二个元素赋值
englishScore[2] = 65;              //为第三个元素赋值
totalScore[0] = mathScore[0] + englishScore[0];    //计算第一个同学的总成绩
totalScore[1] = mathScore[1] + englishScore[1];    //计算第二个同学的总成绩
totalScore[2] = mathScore[2] + englishScore[2];    //计算第三个同学的总成绩
//输出三个同学的总成绩
System.out.println(students[0] + “同学的总成绩为:” + totalScore[0]);
System.out.println(students[1] + “同学的总成绩为:” + totalScore[1]);
System.out.println(students[2] + “同学的总成绩为:” + totalScore[2]);
}
}
这个示例中,先声明四个数组,其中 mathScore 和 englishScore 存储学生的数学和英语成绩, students
存储学生的姓名,totalScore 存储学生的总成绩。通过赋值的方式为数组 englishScore 初始化成绩。访问
mathScore 和 englishScore 数组中对应索引处的元素,相加以后赋值给 totalScore 数组相应的元素,最后
输出三个同学的姓名及其总成绩,如下所示。
张小明同学的总成绩为:176
黄芳同学的总成绩为:165
赵秀丽同学的总成绩为:149
通常数组的大小会远远大于本章中示例中的数组大小,所以在对数组进行操作时,一般都使用循环
来重复一个数组元素,而不需要一个一个单独地处理。关于循环结构,会在第 5 章进行讲解。
2.5.3.4   数组的数组
数组元素除了可以是原始数据类型、对象类型之外,还可以是数组,即数组的元素是数组。所以虽
然 Java 不支持多维数组,但是可以通过声明数组的数组来实现同样的功能。元素数组还可以包含数组,
依此类推,最后创建出达到需要的任意维数。
声明数组的数组语法如下,在类型后面使用两个方括号:
数组类型[ ][ ]  数组名字;           
数组类型  数组名字[ ][ ];           
这两种数组变量声明的方式作用上是相同的,但通常建议采用第一种方式,同声明一维数组类似。
声明了数组变量之后,下一步就需要创建一个数组对象,并将其赋给所声明的数组变量。有两种方
式可以用来创建二维数组对象:使用 new 运算符创建和使用简洁方式创建。
(1)使用 new 运算符
使用 new 运算符来创建数组的数组,如以下代码所示。
int[ ][ ]   year = new int[52][7] ;         
使用 new 运算符来创建数组的数组对象时,必须指定这个数组的大小。在这个代码中,创建了一个
数组的数组对象,用来保存一年中的 52 个星期及每个星期的 7 天。
可以把数组的数组想象成一个二维表格,带有行和列。其中行与二维数组的第一维对应,列与二维
数组的第二维对应。例如,对于下面的代码。
int[ ][ ]   arrays1= new int[3][5] ; 
可以把数组 arrays1 看成是如表 2.1 所示的二维表格。对于二维数组来说,第一个下标代表着所在的
·19·
行,第二个下标代表着所在的列。下标也是从 0 开始计算的。
表 2.1   二维数组结构
列索引0  列索引1  列索引2  列索引3  列索引4
行索引0  arrays[0][0]  arrays[0][1]  arrays[0][2]  arrays[0][3]  arrays[0][4]
行索引1  arrays[1][0]  arrays[1][1]  arrays[1][2]  arrays[1][3]  arrays[1][4]
行索引2  arrays[2][0]  arrays[2][1]  arrays[2][2]  arrays[2][3]  arrays[2][4]
(2)使用简洁方式
也可以通过把数组元素值直接放在大括号中的办法,来同时完成创建和初始化数组的数组。在大括
号中使用逗号分隔每个花括号,每个花括号中为用逗号分开的行数据。这时将在内存中分配与元素数量
相适应的空间大小,并赋予指定的元素值,如以下代码所示。
int[ ][ ]   arrays2 = {{11,12,13,14,15},{21,22,23,24,25},{31,32,33,34,35}}; 
在这里,定义了一个数组 arrays2,它有 3 个元素,每个元素又是一个数组。可以把数组 arrays2 看
成如表 2.2 所示的二维表格。
表 2.2   二维数组arrays2 的结构
列索引0  列索引1  列索引2  列索引3  列索引4
行索引0  11  12  13  14  15
行索引1  21  22  23  24  25
行索引2  31  32  33  34  36
使用这种方式创建数组,数组中每一行的长度也可以不同,如下面的例子所示:
public class ArrayOfArrays{
public static void main(String[] args){
int[][] arrays2 = {
{11,12 },
{21,22,23,24,25},
{31,34,35}
};
System.out.println(arrays2[0][0]);
System.out.println(arrays2[1][0]);
System.out.println(arrays2[2][0]);
System.out.println(arrays2[0][1]);
System.out.println(arrays2[1][4]);
System.out.println(arrays2[2][2);
}
}
编译并运行该示例程序,输出结果为:
11
21
31
12
25
35
通常在对数组的数组进行操作时,一般都使用多重循环来处理。关于循环结构,会在第 5 章进行讲
解。 
20
2.6  小结
Java 程序是由类和对象组成的,而类和对象包含有变量和方法。变量实质上是内存中用来存放程序
待处理数据、中间数据和运算结果数据的空间。通过声明变量并初始化,在内存中为变量分配内存空间
并存储数据。
在声明变量时,要遵循一定的语法规则和命名规则,同时指定变量的数据类型。Java 中有 8 种原始
数据类型,此外还有用来存储批量数据的数组类型。Java 不支持多维数组,但是可以通过声明数组的数
组这种方式,来实现其它编程语言中多维数组的功能。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值