以下为个人学习笔记和习题整理
课程:零基础学 Java 语言 - 浙江大学 - 翁恺 @ 中国大学 MOOC
https://www.icourse163.org/course/ZJU-1001541001

# 课堂笔记

# 字符类型 char

  • 字符也是 Java 中基础的数据类型之一
    • 单引号表示的字符: 'a' , '1'
  • Java 采用 Unicode16 表达字符,在所有的机器上,不管 CPU、操作系统和本地语言,字符类型是一致和统一的。
  • 一个汉字也是 Unicode 的一个字符,所以也是 Java 的一个字符。

# 字符计算

char c = 'A';
c++;
System.out.println(c); // 输出结果为:B
int i = 'Z'-'A';
System.out.println(i); // 输出结果为:25
System.out.println((int)c); // 输出结果为:66
  • 一个字符加一个数字得到 Unicode 码表中的那个数之后的字符
  • 两个字符的减,得到它们在表中的距离
  • char 也可以和 int 之间相互赋值,输出字符在 Unicode 码表中的位置

# 大小写转换

  • 字母和数字在 Unicode 表中是顺序排列的
  • 大写字母和小写字母是分开排列的,不在一起
  • 'a' - 'A' 可以得到两段之间的距离
  • a + 'a' - 'A' 可以把一个大写字母变成小写字母
  • a + 'A' - 'a' 可以把一个小写字母变成大写字母

# 字符大小比较

  • 字符可以比较大小,依据是它们在 Unicode 表中的编号

    '0' < '9'
    'A' < 'Z'
    'a' > 'Z'
    'Z' < 'a'

# 逃逸字符

  • 用来表达无法印出来的控制字符或特殊字符,它由一个反斜杠 "\" 开头,后面跟上另一个字符,这两个字符合起来,组成了一个字符。
字符意义字符意义
\b回退一格(但不删除)"双引号
\t到下一个表格位单引号
\n换行\反斜杠本身
\r回车

# 包裹类型

  • 对于基本数据类型,Java 提供了对应的包裹 (wrap) 类型。

  • 这些包裹类型将一个基本数据类型的数据转换成对象的形式,从而使得它们可以像对象一样参与运算和传递。

  • 下表列出了基本数据类型所对应的包裹类型:

基本类型包裹类型
booleanBoolean
charCharacter
byteByte
shortShort
intInteger
longLong
floatFloat
doubleDouble
  • 除了 int 和 char 以外,包裹类型就是把基本类型的名字的第一个字母大写。
  • 在 Java 的系统类库中,所有第一个字母大写的,都是类的名字。所以在编辑程序的时候,一定要小心大小写,以免一不小心犯错。
// 定义包裹类型变量
Integer i = 10;
Integer i = new Integer(10);
Integer i = new Integer("10");
// 获得包裹类型的值
Integer iii = 10;
int i = iii;

# 用途

  • 当需要让一个类或对象做事情的时候,使用 . 运算符。

  • 获得该类型的最大最小值

Integer.MIN_VALUE
Integer.MAX_VALUE
  • 判断这个字符是否是数字
static boolean isDigit(char ch)
  • 判断这个字符是不是字母
static boolean isLetter(char ch)
  • 判断这个字符是不是字母或数字
static boolean isLetterOrDigit(char ch)
  • 判断这个字符是不是⼩写字母
static boolean isLowerCase(char ch)
  • 判断这个字符是不是⼤写字母
static boolean isUpperCase(char ch)
  • 判断这个字符是不是⼀种空格
static boolean isWhitespace(char ch)
  • 把这个字符转换成⼩写
static char toLowerCase(char ch)
  • 把这个字符转换成⼤写
static char toUpperCase(char ch)

# 字符串

  • 双引号括起来的 0 个或多个字符就是一个字符串字面量
    “hello” “1” “”

# 输入字符串

  • 读入一个单词,单词的标志是空格、tab、换行
in.next();
  • 读入一整行
in.nextLine();

# 字符串变量 String

String s;
  • String 是一个类。
  • String 的变量和数组变量类似,它并不存放字符串,不是字符串的所有者,它是字符串的管理者。

# new 创建对象

String s = new String("a string");
  • 创建了一个 String 的对象
  • 用 "a string" 初始化这个对象
  • 创建管理这个对象的变量 s
  • 让 s 管理这个对象
graph BT
A(a string)
B((s))
B --管理-->A
String s = "hello";
  • 编译器创建一个 String 类的对象交给 s 来管理

# 变量赋值

graph TB
A(String a)
B(String b)
C[一个字符串]
A --new-->C
B --b=a-->C
  • 字符串变量中,a、b 是管理者,不是所有者。b=a 是 b 和 a 都管理 a 的字符串。
  • int 变量中,a、b 是所有者,b=a 是改变本身。

# 内容比较 equals

  • 比较是否同一个
if( input == "bye" ) {
    ...
}
  • equals 比较内容是否相同
if( input.equals("bye") ) {
    ...
}

# 字符串连接 +

  • 用加号 (+) 可以连接两个字符串
    "hello" + "world""helloworld"
  • + 的一边是字符串而另一边不是时,会将另一边表达为字符串,然后做连接
    "I’m " + 18"I’m 18"
    1 + 2 + "age""3age"
    "age" + 1 + 2"age12"

# 字符串运算 .

  • 字符串是对象,对它的所有操作都是通过 . 这个运算符来进行的
字符串.操作
  • . 左边的这个字符串,做右边的那个操作

  • 左边的字符串可以是变量,也可以是常量

  • Java 的字符串是一种特殊的 不可变 对象,所有的字符串操作都是产生一个新的字符串,而不是对原来的字符串的修改。

String s = "abc";
System.out.println(s.toUpperCase()); // ABC
System.out.println(s); // abc

# 大小比较 compareTo

s1.compareTo(s2)
s1.compareToIgnoreCase(s2)// 可以不区分大小写地比较大小
  • 如果 s1 比 s2 小,那么结果是负的
  • 如果 s1 和 s2 相等,那么结果是 0
  • 如果 s1 比 s2 大,那么结果是正的

# 获得长度 length ()

String name = "Hellola";
name.length(); // 输出: 7
String str1 = "one";
str1.length(); // 输出:3
String str2 = "";
str2.length(); // 输出: 0
String str3;
str2.length(); // Error! 因为 str3 没有管理任何 String 对象

# 访问字符串里的字符 charAT

s.charAT(index)
  • 返回在 index 上的单个字符
  • index 的范围是 0length()-1
  • 第一个字符的 index 是 0,和数组一样
  • 但是不能用 for-each 循环来遍历字符串

# 得到子串 substring

s.substring(n)
  • 得到从 n 号位置到末尾的全部内容
s.substring(b,e)
  • 得到从 b 号位置到 e 号位置之前的内容

# 寻找字符 indexOf

s.index0f(c)
  • 得到 c 字符所在的位置,-1 表示不存在
s.index0f(c,n)
  • 从 n 号位置开始寻找 c 字符
s.index0f(t)
  • 找到字符串 t 所在的位置
s.lastIndex0f(c)
s.lastIndex0f(c,n)
s.lastIndex0f(t)
  • 从右边开始找,各部分参数同上

# 以 x 起始或结束 startsWith endsWith

s.startsWith(t)
s.endsWith(t)

# 去除两端空格 trim

s.trim()

# 内容替换 replace

s.replace(c1,c2)

# 大小写转换 toLowerCase toUpperCase

s.toLowerCase()
s.toUpperCase()

# 编程题

# 题目 1. 单词长度(5 分)

  • 题目内容
    你的程序要读入一行文本,其中以空格分隔为若干个单词,以 . 结束。你要输出这行文本中每个单词的长度。这里的单词与语言无关,可以包括各种符号,比如 “it's” 算一个单词,长度为 4。注意,行中可能出现连续的空格。

  • 输入格式
    输入在一行中给出一行文本,以 . 结束,结尾的句号不能计算在最后一个单词的长度内。

  • 输出格式
    在一行中输出这行文本对应的单词的长度,每个长度之间以空格隔开,行末没有最后的空格。

  • 输入样例
    It's great to see you here.

  • 输出样例
    4 5 2 3 3 4

# 解题代码

import java.util.Scanner;
public class Main {
    
    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);
        
        String s = in.next();// 字符串输入
        String comma = "";
        int len; // 字符串长度
        
        while ( true ) {
            len = s.length();
            
            if (s.endsWith(".") ) {
                len -= 1;
                if (len > 0) {
                    System.out.print(comma + len);
                }               
                break;
            }
            
            System.out.print(comma + len);
            
            s = in.next();// 下一个字符串输入
            comma = " "; // 下一个字符串前有空格
        }
                
    }
}

# 题目 2. GPS 数据处理(5 分)

  • 题目内容
    NMEA-0183 协议是为了在不同的 GPS(全球定位系统)导航设备中建立统一的 BTCM(海事无线电技术委员会)标准,由美国国家海洋电子协会(NMEA-The National Marine Electronics Associa-tion)制定的一套通讯协议。GPS 接收机根据 NMEA-0183 协议的标准规范,将位置、速度等信息通过串口传送到 PC 机、PDA 等设备。

    NMEA-0183 协议是 GPS 接收机应当遵守的标准协议,也是目前 GPS 接收机上使用最广泛的协议,大多数常见的 GPS 接收机、GPS 数据处理软件、导航软件都遵守或者至少兼容这个协议。

    NMEA-0183 协议定义的语句非常多,但是常用的或者说兼容性最广的语句只有 $GPGGA、$GPGSA、$GPGSV、$GPRMC、$GPVTG、$GPGLL 等。

    其中 $GPRMC 语句的格式如下:

    $GPRMC,024813.640,A,3158.4608,N,11848.3737,E,10.05,324.27,150706,,,A*50

    这里整条语句是一个文本行,行中以逗号 , 隔开各个字段,每个字段的大小(长度)不一,这里的示例只是一种可能,并不能认为字段的大小就如上述例句一样。

    字段 0:$GPRMC,语句 ID,表明该语句为 Recommended Minimum Specific GPS/TRANSIT Data(RMC)推荐最小定位信息
    字段 1:UTC 时间,hhmmss.sss 格式
    字段 2:状态,A = 定位,V = 未定位
    字段 3:纬度 ddmm.mmmm,度分格式(前导位数不足则补 0)
    字段 4:纬度 N(北纬)或 S(南纬)
    字段 5:经度 dddmm.mmmm,度分格式(前导位数不足则补 0)
    字段 6:经度 E(东经)或 W(西经)
    字段 7:速度,节,Knots
    字段 8:方位角,度
    字段 9:UTC 日期,DDMMYY 格式
    字段 10:磁偏角,(000 - 180)度(前导位数不足则补 0)
    字段 11:磁偏角方向,E = 东 W = 西
    字段 16:校验值

    这里, * 为校验和识别符,其后面的两位数为校验和,代表了 $* 之间所有字符(不包括这两个字符)的异或值的十六进制值。上面这条例句的校验和是十六进制的 50,也就是十进制的 80。

    提示: ^ 运算符的作用是异或。将 $* 之间所有的字符做 ^ 运算 (第一个字符和第二个字符异或,结果再和第三个字符异或,依此类推) 之后的值对 65536 取余后的结果,应该和 * 后面的两个十六进制数字的值相等,否则的话说明这条语句在传输中发生了错误。注意这个十六进制值中是会出现 A-F 的大写字母的。另外,如果你需要的话,可以用 Integer.parseInt(s) 从 String 变量 s 中得到其所表达的整数数字;而 Integer.parseInt(s, 16) 从 String 变量 s 中得到其所表达的十六进制数字。

    现在,你的程序要读入一系列 GPS 输出,其中包含 $GPRMC,也包含其他语句。在数据的最后,有一行单独的 END 表示数据的结束。

    你的程序要从中找出 $GPRMC 语句,计算校验和,找出其中校验正确,并且字段 2 表示已定位的语句,从中计算出时间,换算成北京时间。一次数据中会包含多条 $GPRMC 语句,以最后一条语句得到的北京时间作为结果输出。

    你的程序一定会读到一条有效的 $GPRMC 语句。

  • 输入格式
    多条 GPS 语句,每条均以回车换行结束。最后一行是 END 三个大写字母。

  • 输出格式
    6 位数时间,表达为: hh:mm:ss
    其中,hh 是两位数的小时,不足两位时前面补 0;mm 是两位数的分钟,不足两位时前面补 0;ss 是两位数的秒,不足两位时前面补 0。

  • 输入样例
    $GPRMC,024813.640,A,3158.4608,N,11848.3737,E,10.05,324.27,150706,,,A*50
    END

  • 输出样例
    10:48:13

# 解题代码

import java.util.Scanner;
public class Main {
    
    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);
        
        String str = in.next();// 字符串输入
        String substr = "";
        Integer check, hh = 0, mm = 0, ss = 0;
        int code = 0;
        
        while ( !str.equals("END") ) {  
            
            if ( !str.startsWith("$GPRMC")) {
                str = in.next();// 下一个字符串输入
                continue;
            }
            
            // 将 $ 和 * 之间所有的字符做 ^ 运算
            substr = str.substring(1, str.indexOf("*"));
            // 获得 * 后的校验符的十六进制数
            check = Integer.parseInt(str.substring(str.indexOf("*")+1), 16);
            
            for(int i = 0; i < substr.length(); i++) {
                code ^= substr.charAt(i);
            }
            
            if (code % 65536 == check) { // 数据合法
                String[] strs = str.split(",");
                
                if (strs[2].equals("A")) { //  已定位
                    
                    hh = Integer.parseInt(strs[1].substring(0, 2));
                    mm = Integer.parseInt(strs[1].substring(2, 4));
                    ss = Integer.parseInt(strs[1].substring(4, 6));
                    
                    // 输出北京时间
                    hh = ( hh + 8 ) % 24;
                    if ( hh < 10 ) {
                        System.out.print("0");
                    }
                    System.out.print(hh+":"+mm+":"+ss);                     
                }               
            }
                        
            str = in.next();// 下一个字符串输入
        }
                
    }
}
阅读次数

请我喝[茶]~( ̄▽ ̄)~*

Ruri Shimotsuki 微信支付

微信支付

Ruri Shimotsuki 支付宝

支付宝

Ruri Shimotsuki 贝宝

贝宝