一.Java程序基础

1.Java程序基本结构

Java版HelloWorld

public class Hello{
    public static void main(String[] args){
        System.out.println("Hello,world!")
    }
}

Java程序的基本单位为class,此代码中class名字就是Hello,class前面的public为访问修饰符。

类名要求:

  • 类名必须以英文字母开头,后接字母,数字和下划线的组合
  • 通常以大写字母开头
  • 如果名字是由多个单词组成,每个单词的首字母大写

命名规范的示例:

  • Hello
  • NoteBook

在class内部可以定义多种方法(method):

public class Hello {
    public static void main(String[] args) { // 方法名是main
        // 方法代码...
    } // 方法定义结束
}

这里方法名为main,返回值为void,public等修饰符也可以修饰方法,

Java入口程序规定的方法必须是静态方法,方法名必须为main,括号内的参数必须是String数组。

方法名与类名相似,但是规则要求首字母小写。

示例:

  • main
  • goodNight
  • play

方法内部的语句为真正的执行代码,语句和注释的相关使用与c语言相似,在这里不再赘述。

2.变量和数据类型

Java中的变量分为两种:基本类型的变量和引用类型的变量

基本类型的变量是“持有”某个数值,引用类型的变量是“指向”某个对象。

基本数据类型(与c相似)
  • 整数类型:byte,short,int,long
  • 浮点数类型:float,double
  • 字符类型:char
  • 布尔类型:boolean

注意:

  1. 对于float类型,需要加上f后缀。
  2. char类型使用单引号',且仅有一个字符,要和双引号"的字符串类型区分开。
引用类型

除了基本类型,剩下都是引用类型,例如String

常量

加上final修饰符,变量就变成了常量:

final double PI=3.1415926//PI变为常量

常量在定义时进行初始化后就不可再次赋值,再次赋值会导致编译错误。

根据习惯,常量名通常全部大写

var关键字

有些时候,类型的名字太长,写起来比较麻烦。例如:

StringBuilder sb = new StringBuilder();

这个时候,如果想省略变量类型,可以使用var关键字:

var sb = new StringBuilder();

编译器会根据赋值语句自动推断出变量sb的类型是StringBuilder。对编译器来说,语句:

var sb = new StringBuilder();

实际上会自动变成:

StringBuilder sb = new StringBuilder();

因此,使用var定义变量,仅仅是少写了变量类型而已。

变量的作用范围

规则同c。

定义变量时,要遵循作用域最小化原则,尽量将变量定义在尽可能小的作用域,并且,不要重复使用变量名。

运算优先级

在Java的计算表达式中,运算优先级从高到低依次是:

  • ()
  • ! ~ ++ --
  • * / %
  • + -
  • << >> >>>
  • &
  • |
  • += -= *= /=

关系运算符的优先级从高到低依次是:

  • !
  • >>=<<=
  • ==!=
  • &&
  • ||

通常加括号保证运算的优先级即可。

浮点数运算注意事项

需要特别注意,在一个复杂的四则运算中,两个整数的运算不会出现自动提升的情况。例如:

double d = 1.2 + 24 / 5; // 5.2

计算结果为5.2,原因是编译器计算24 / 5这个子表达式时,按两个整数进行运算,结果仍为整数4

布尔运算注意事项

布尔运算的一个重要特点是短路运算。如果一个布尔运算的表达式能提前确定结果,则后续的计算不再执行,直接返回结果。

因为false && x的结果总是false,无论xtrue还是false,因此,与运算在确定第一个值为false后,不再继续计算,而是直接返回false

字符和字符串

字符类型与c相似,不同的地方在Unicode编码,比如使用转义字符\u+Unicode编码来表示一个字符:

// 注意是十六进制:
char c3 = '\u0041'; // 'A',因为十六进制0041 = 十进制65
char c4 = '\u4e2d'; // '中',因为十六进制4e2d = 十进制20013

字符串类型为本次Java学习之旅的重点,因为大创的关键就是字符串处理。

字符串类型String是引用类型,我们用双引号"..."表示字符串。

String s = ""; // 空字符串,包含0个字符
String s1 = "A"; // 包含一个字符
String s2 = "ABC"; // 包含3个字符
String s3 = "中文 ABC"; // 包含6个字符,其中有一个空格

如果需要表示",可以借助转义字符。

String s = "abc\"xyz"; // 包含7个字符: a, b, c, ", x, y, z
String s = "abc\\xyz"; // 包含7个字符: a, b, c, \, x, y, z

常见的转义字符包括:

  • \" 表示字符"
  • \' 表示字符'
  • \\ 表示字符\
  • \n 表示换行符
  • \r 表示回车符
  • \t 表示Tab
  • \u#### 表示一个Unicode编码的字符

例如:

String s = "ABC\n\u4e2d\u6587"; // 包含6个字符: A, B, C, 换行符, 中, 文

字符串连接

Java的编译器对字符串做了特殊照顾,可以使用+连接任意字符串和其他数据类型,这样极大地方便了字符串的处理。例如:

public class Main {
    public static void main(String[] args) {
        String s1 = "Hello";
        String s2 = "world";
        String s = s1 + " " + s2 + "!";
        System.out.println(s);
    }
}
//输出为Hello world!

如果用+连接字符串和其他数据类型,会将其他数据类型先自动转型为字符串,再连接:

public class Main {
    public static void main(String[] args) {
        int age = 25;
        String s = "age is " + age;
        System.out.println(s);
    }
}
输出为age is 25

多行字符串

从Java 13开始,字符串可以用"""..."""表示多行字符串。例如:

public class Main {
    public static void main(String[] args) {
        String s = """
                   SELECT * FROM
                     users
                   WHERE id > 100
                   ORDER BY name DESC
                   """;
        System.out.println(s);
    }
}
/*输出为
SELECT * FROM
  users
WHERE id > 100
ORDER BY name DESC

*/

上述多行字符串实际上是5行,在最后一个DESC后面还有一个\n。如果我们不想在字符串末尾加一个\n需要在最后改成 ORDER BY name DESC""";

还需要注意到,多行字符串前面共同的空格会被去掉,即:

String s = """
...........SELECT * FROM
...........  users
...........WHERE id > 100
...........ORDER BY name DESC
...........""";

如果多行字符串的排版不规则,那么,去掉的空格就会变成这样:

String s = """
.........  SELECT * FROM
.........    users
.........WHERE id > 100
.........  ORDER BY name DESC
.........  """;

即总是以最短的行首空格为基准。

不可变特性

public class Main {
    public static void main(String[] args) {
        String s = "hello";
        System.out.println(s); // 显示 hello
        s = "world";
        System.out.println(s); // 显示 world
    }
}
/*输出
hello
world
*/

在这里,字符串s其实没有变,变的是s的指向,和指针相似,在JVM虚拟机中根据执行顺序依次创建了helloworld,而s是负责指向这两个字符,当执行到String s = "hello"时,指向hello,当执行到s = "world";时,指向world。也就是说,字符串"hello"还在,但是s指向变了。

public class Main {
    public static void main(String[] args) {
        String s = "hello";
        String t = s;
        s = "world";
        System.out.println(t); // t是"hello"还是"world"?
    }
}
//输出为:hello

空值null

引用类型的变量可以指向一个空值null,它表示不存在,即该变量不指向任何对象。例如:

String s1 = null; // s1是null
String s2; // 没有赋初值值,s2也是null
String s3 = s1; // s3也是null
String s4 = ""; // s4指向空字符串,不是null

注意要区分空值null和空字符串"",空字符串是一个有效的字符串对象,它不等于null

数组类型

定义一个数组类型的变量,使用数组类型“类型[]”,例如,int[]。和单个基本类型变量不同,数组变量初始化必须使用new int[5]表示创建一个可容纳5个int元素的数组。

Java的数组特点:

  • 数组所有元素初始化为默认值,整型都是0,浮点型是0.0,布尔型是false
  • 数组一旦创建后,大小就不可改变。

可以用数组变量.length获取数组大小:

public class Main {
    public static void main(String[] args) {
        // 5位同学的成绩:
        int[] ns = new int[5];
        System.out.println(ns.length); // 5
    }
}

可以在定义数组时直接指定初始化的元素,这样就不必写出数组大小,而是由编译器自动推算数组大小。例如:

public class Main {
    public static void main(String[] args) {
        // 5位同学的成绩:
        int[] ns = new int[] { 68, 79, 91, 85, 62 };
        System.out.println(ns.length); // 编译器自动推算数组大小为5
    }
}

字符串数组

public class Main {
    public static void main(String[] args) {
        String[] names = {"ABC", "XYZ", "zoo"};
        String s = names[1];
        names[1] = "cat";
        System.out.println(s); // s是"XYZ"还是"cat"?
    }
}
//输出:XYZ

二.流程控制

1.输入与输出
输出

输出常用的为System.out.println(),这里的println为print line的缩写,表示输出并换行,如果不想换行,可以使用print()

public class Main {
    public static void main(String[] args) {
        System.out.print("A,");
        System.out.print("B,");
        System.out.print("C.");
        System.out.println();
        System.out.println("END");
    }
}
/*输出:
A,B,C.
END
*/

Java的格式化功能提供了多种占位符,可以把各种数据类型“格式化”成指定的字符串:

占位符说明
%d格式化输出整数
%x格式化输出十六进制整数
%f格式化输出浮点数
%e格式化输出科学计数法表示的浮点数
%s格式化字符串

注意,由于%表示占位符,因此,连续两个%%表示一个%字符本身。

输入
import java.util.Scanner;

public class Main {
    public static void main(String[] args) {
        Scanner scanner = new Scanner(System.in); // 创建Scanner对象
        System.out.print("Input your name: "); // 打印提示
        String name = scanner.nextLine(); // 读取一行输入并获取字符串
        System.out.print("Input your age: "); // 打印提示
        int age = scanner.nextInt(); // 读取一行输入并获取整数
        System.out.printf("Hi, %s, you are %d\n", name, age); // 格式化输出
    }
}

首先,我们通过import语句导入java.util.Scannerimport是导入某个类的语句,必须放到Java源代码的开头。

然后,创建Scanner对象并传入System.in

有了Scanner对象后,要读取用户输入的字符串,使用scanner.nextLine(),要读取用户输入的整数,使用scanner.nextInt()Scanner会自动转换数据类型,因此不必手动转换。

2.if判断

引用类型判断内容相等要使用equals(),注意避免NullPointerException

其余同c,不再赘述。

3.switch多重选择

保证breakdefault的存在

编译检查

使用IDE时,可以自动检查是否漏写了break语句和default语句,方法是打开IDE的编译检查。

在Eclipse中,选择Preferences - Java - Compiler - Errors/Warnings - Potential programming problems,将以下检查标记为Warning:

  • 'switch' is missing 'default' case
  • 'switch' case fall-through

在Idea中,选择Preferences - Editor - Inspections - Java - Control flow issues,将以下检查标记为Warning:

  • Fallthrough in 'switch' statement
  • 'switch' statement without 'default' branch

switch语句存在问题时,即可在IDE中获得警告提示。

4.循环

whiledo whilefor三种基本类型。

在Java中还提供了另一种for each循环,它可以更简单地遍历数组:

public class Main {
    public static void main(String[] args) {
        int[] ns = { 1, 4, 9, 16, 25 };
        for (int n : ns) {
            System.out.println(n);
        }
    }
}
/*输出:
1
4
9
16
25
*/
5.break和continue

break跳出最近的一层循环;

continue提前结束当前循环,再执行下一次循环。

最后修改:2021 年 07 月 29 日 07 : 49 PM
如果觉得我的文章对你有用,请随意赞赏