Java 语言程序设计复习笔记

第一章 java语言简介

  1. JVM的实现叫做java运行时系统或者运行时环境;
  2. JDK是软件开发工具包,其中包含编写和运行java程序的所有工具
  • javac 编译器
  • java 字节码解释器
  • javaAppletViewer 小应用程序浏览工具;
  • jdb java 调试器
  • javap 反编译 将类文件还原成方法和变量
  • javadoc 文档生成器, 创建html文件
  1. package 每个文件只能有且只有1个并且只能放在文件的最前面。表示该文件所在的包中;
  2. import 语句个数不限,必须放在所有类定义之前;
  3. 每个文件中只能并且至少有一个公有类,文件名的和公有类的名字必须一致,非共有类 不限制;
  4. java 采用的是解释执行方式,解释器是java.exe,JVM通过解释器执行类文件;

习题

  1. 概述java语言的特点;

java是一种面向对象的高级编程语言,它的所有语句都包含在类的定义中;语句格式非常类似于C++;java是强类型语言;它的解释器只占用很少的内存,适合在绝大多数类型的机器上运行。

  1. 什么是java虚拟机?它包括那几部分?

可以将JVM看作是编译后的java程序和硬件系统之间的接口,java屏蔽了硬件平台的差异性,正因为这个特性, java才可以做到平台无关性。
JVM的具体实现包括:指令集、寄存器组、类文件格式、栈、垃圾收集堆、内存区。

  1. 解释如何从命令行中获取传递给主函数的值?

命令行参数是动态传给程序的参数,将多个参数放入到main函数中的数组中。
分隔符是空格;

  1. 命令行参数的作用是什么?多个参数之间的分隔符是什么?

传递给执行程序,在程序中可以使用命令行中的参数

  1. 运行java程序需要几步?各步的命令是什么?

分两步: 第一步先编译,使用命令工具 javac + 文件地址,生成一个字节码文件;第二步就是通过解释器执行类文件 java + 类文件;

第2章 面向对象程序设计技术

  1. 面向对象程序设计分三个步骤: 面向对象的分析、面向对象的设计、面向对象的程序设计;
  2. 类用来描述具有相同特性的一类事物,其中不同属性值的个体称为对象;

习题

  1. 简述类及对象的概念;

类就是描述具有相同特性的一类事物,其中具有不同属性的个体称为对象;

  1. 简述面向对象程序设计方法的特性;

重要特性就是 封装、继承、多态;
封装:讲数据及数据法人操作捆绑在一起成为类,类外的代码应该不能直接访问类内声明的变量并修改变量的值。只能通过调用方法的的形式和封装在类中的数据进行交互;

  1. 简述java中的继承机制特点;

继承关系具有传递性,子类可以继承父类的特性,父类又可以继承它自己父类的特性,原则上子类可以继承所有祖先类的特性。子类还可以扩展自己的属性;

  1. 简述java中多重继承的实现机制;

java语言理论上不支持多种继承,但是可以结合实现多个接口,达到多重继承的类似效果;

  1. 为什么java不再使用C++中采用的多继承机制?

多重继承的关系就是一张网,而单继承的关系就是一棵树,单继承更为简单清晰,多继承由于继承的特性,导致可能带来混乱。如果父类中有同名的方法,子类到底应该使用哪个方法;

第3章 基本数据类型和标识符

  1. /***/ 是文档注释,可用来生成java文档。可借助javadoc工具,可生成专门的文档;
  2. 标识符的字母区分大小写,在长度上没有限制,只要计算机的内存容量能够满足;
  3. 尽量不要在方法名和变量名中使用下划线和美元符号,因为该字符内层类有特殊含义。常量名中均使用大写,字与字之间用下划线分割;
  4. java中没有二进制形式的常量;
  5. 默认的浮点数常量是double型的;
  6. java的使用的Unicode字符集,它使用16位表示一个字符,使用char定义一个字符;ASCII码是Unicode子集;
  7. 如果再说明前定义了final关键字修饰符,则表明这个变量被说明成一个常量 ,它的值不可修改;
  8. 声明的基本数据变量如果没有初始化,编译时会报错;static修饰基本数据类型的静态变量会有默认值;如int的默认值就是0;不能定义局部静态变量;

习题

  1. java中共有哪些基本数据类型,他们分别用什么符号表示,各自取值范围有多大?
基本数据类型 符号 取值范围 占用字节数
整型 byte -128~127 1
整型 short -32768-32767 2
整型 int 4
整型 long 8
字符类型 char 2
逻辑类型 boolean 1

为什么正数的会比负数小一位呢?
因为二进制的运算导致的,比如正1加上负1,从中引入了补码和反码的概念。底层在做运算的时候就是正数1的原码加上-1的补码才会等于0;其中补码在反码的结果上+1。换成二进制也就是00000001 + 11111111 = 0;二进制的反码只需要取反非符号位,并且只有负数的反码才会变化,正数的反码和补码是一样的;

第四章流程控制

  1. java中的自动类型转换都将占内存位数少的类型转换为占内存位数多的类型,只有byte和short是例外,当两个数都为byte或者short时,他们都会被转换成int类型。这是因为JVM内部以4字节为数据处理的单元,所以系统将不足32位的数据转换成32位,然后进行运算;
    当左操作数是int时,右侧操作数会先以32取模
  2. java中字符是无符号的,负整数讲转换为与原数毫无关系的一个字符。转换类型不能用于布尔值;
  3. 逻辑右移运算符>>> ,也叫无符号右移,逻辑右移操作总是得到一个非负数;
  4. switch语句中的表达式结果的类型必须是整数赋值相容的,可以是int、byte。short、char,而byte和short都会自动转换成int类型;
  5. break和continue 后面可以跟一个标号,达到内层循环控制外层循环;
test1: for (int i = 0; i< 10; i++) {

            for (int j = 0; j< 10; j++) {

                break test1;


            }

        }
  1. 输入Scanner类,创建对象时接收一个输入源,如system.in默认是键盘;通过调用next获取一个输入的数值,数值之间用空格符分隔。 每次调用next都会阻塞直接到获取到输入信息,但是可以收入多个,后面的next就会依次接着读取;
  2. 输出格式化,java中利用NumberFormat和DecimalFormat格式化输出内容;
  3. 除了字符串可以和其他基本类型做加法,int + char 或者 double + char等,其他基本类型之间不可以;

第五章 类与对象

  1. friendly是默认的权限修饰符,只对包内的中类可以访问;
  2. 一个类文件可以不含有公有类,默认就是friendly修饰类,但是必须得得指定包名,使在同一个包内可以访问。除了内部类不能有定义其他私有类,因为这样其他地方访问不到,没有意义;
  3. 一个变量的指针地址占用两个字节;
  4. java属于值传递,基本类型直接传递值,对象类型直接传递对象的引用地址;
  5. 程序运行时可以使用instanceof运算符来判明一个引用指向的具体实例;
if (p instanceof Person) {
  //....
}
  1. 使用static描述的变量叫做静态变量或者类变量;
  2. 用final说明的常量必须在说明时给出初值,之后不可再修改;
  3. 如果一个类被final定义终极类,那么它的方法也都会变成终极方法;同时final也可以修饰对象变量,使对象变量的地址值不可修改;
  4. 使用abstract定义抽象类,抽象类不能直接使用,需要子类去继承后使用子类。只要类中有一个方法被定义为抽象方法,这个类就必须被定义为抽象类;
  5. 当子类继承父类时,父类如果自定义了一个且只有一个构造方法,子类必须在自己的构造方法中调用父类的构造方法;因为构造方法不能被继承;
class Student extends Person {
    Student() {
      super(10,20);
    }
}
class Person  {

    double weight;
    int age;
    Person(int age, double weight) {

        this.age = age;
        this.weight = weight;
        System.out.println("initialize Person");
    }
}
  1. 当子类继承的是一个抽象类时,子类必须实现所有的抽象方法,否则子类还是抽象类;
  2. 在接口中定义的成员变量 默认都是终极变量,在声明时必须哟赋值初值;
  3. 在类中实现一个接口使用implements,类中必须实现所有的接口方法;接口当当与一个特殊的抽象类;
  4. 包是java提出的独特的概念,表示类的集合。在系统内部,完整的类名是由报名加类组成的;
  5. 包中还可以有包,形成嵌套的关系;包对应的目录通常由系统的classpath来指定;
  6. 使用import 包名.* 可以方便的访问包中的每一个类。但是会占用过多的内存空间;
  7. 类中还可以定义内部类,也叫嵌套类,内部类可以是公有的;当编译时会生成两个字节码文件,如:外部类.class和外部类$内部类.class; 内部类只能在它所属的外部类中使用,在内部类中也可以直接访问外部类中的成员变量和方法;

习题

  1. 什么是类? 什么是面向对象的程序设计方法?

类也是一种数据类型,更像是一个模板,规定了一种数据结构的原型;

第6章 数组、容器、字符串

  1. java中的数组可以是基本数据类型也可以是类类型;
  2. 定义数组在静态声明时不可以指定数组大小,动态初始化方式可以指定数组大小;
静态方式: 类型[] 数组名 =  {};
动态方式 :类型[] 数组名 = new 类型[数组大小];
  1. 一个容器可以保存多种不同的数据类型,java的容器有是三种:List、Set、Map; List 是有序组成的元素;Set具有集合的特性,是一个不包含重复元素的容器,并且最多只包含一个null;这么容器都可以自动调整容量;
  2. 字符串的对象有String和StringBuffer,前者是不可变,后者是可变的;在为StringBuffer对象分配内存时,出去字符所占的空间外,再加上另外16个字符大小的缓冲区;

习题

  1. 用数组实现插入排序;
         int [] array = {2,5,1,4,6,7,8,9,0,3};
         public int[] sort_asc(int [] array) {

            for (int i = 1; i < array.length; i ++) {
                for (int j = i; j > 0; j--) {

                    if (array[j] <= array[j - 1]) {
                        int temp = array[j];
                        array[j] = array[j - 1];
                        array[j-1] = temp;
                    }
                }
            }
            return array;
        }

  1. 基于第一题实现二分查找
 public int searchForHalf(int n) {

            // 数组的内容必须经过排序
            int [] array = this.sort_asc(this.array);
            int result = -1;
            int low = 0;
            int high = array.length - 1;
            int middle = array.length / 2;
            int count = 0;
            while (low <= high) {
                count++;
                middle = (low + high) / 2;
                if (array[middle] == n) {
                    result = middle;
                    break;
                }
                if (array[middle] > n) {
                    high = middle - 1;
                }
                if (array[middle] < n) {
                    low = middle + 1;
                }
            }
            String print = (result == -1) ? " 查找失败" : "查找成功----" + result;
            System.out.println("查询" + count + "次");
            System.out.println(print);
            return result;
        }

第7章 java语言中的异常

  1. java.lang.Throwable是使用异常处理机制中可能抛出并捕获的所有异常的父类;异常分两块分别是Error和Exception,前者表示很难恢复的错误,后者表示设计或者实现方面的问题;Error 不应该被捕获;
  2. 异常发生后,java运行时系统从生成对象的代码块进行回溯,沿着方法的调用栈逐层回溯,寻找相应的处理代码知道找到包含相应异常处理的方法为止,并把异常对象交给该方法处理,这就是捕获(catch)的过程;
  3. 在下列情况下使用异常机制:

1、 当方法因为自身无法控制的原因而不能完成任务;
2、文件不存在、网络连接无法建立等;
3、处理在方法、类库、类中抛出的异常;
4、 在大的项目中采用统一的方式处理异常时;
5、 编写文字处理器一类的程序;
6、 不经常发生但可能发生的鼓掌;

  1. 捕获异常的代码如下:
    即使在try块中包含了return、break、continue、throw等语句,finally语句块最终也会只执行。
try {
            
        } catch (Exception e) {
            
            
        } finally {
            
        }

第8章 图形用户界面设计

  1. java中建立一个GUI程序至少需要3类对象:组件、事件、监听器;
  2. 编写GUI程序分3步走:

1、实例化并建立必要的组件;
2、定义当具体事件发生时的对策从而实现监听器类;
3、建立监听器和产生感兴趣事件的组件之间的联系;

  1. java早起的JDK使用的是抽象窗口工具集AWT,后期出现功能更强的Swing。
AWT类关系图

Swing类关系图

Swing 组件的功能多数会覆盖AWT组件的功能。Swing更加轻量级,更方便于进行平台移植;

  1. 能够容纳其他组件的叫做容器,设计程序时,最外层的组件必须是容器;Swing中有4中顶层容器:JFrame、JApplet、JDialog、JWindow;

1、JFrame是一个独立窗口,它带有标题行和控制按钮,一般用来创建应用程序;
2、 JApplet是用来创建小应用程序的容器,在浏览器窗口中运行;
3、JDialog是对话框;
4、JWindow是一个不带有标题行和控制按钮的窗口,通常很少使用;

  1. 如果需要王容器中添加组件,需要先获取容器中的内容面板getContentPane,然后再往面板中添加组件;
public static void main(String[] args) {

        // 创建容器
        JFrame frame  = new JFrame("Jframe");
        // 创建一个按钮
        JButton button = new JButton("a frame");
        // 获取内容面板
        frame.getContentPane().add(button);
        // 设置最小的显示尺寸
        frame.setMinimumSize(new Dimension(200, 200));
        // 使容器展开 按照子内容
        frame.pack();
        // 使容器可见
        frame.setVisible(true);

    }
  1. 布局管理器,通过给容器和内容面板的setLayout方法设置布局的方式,主要的布局管理器有以下几种:
    常用的主要是三种:FlowLayout BorderLayout GridLayout;

1、BorderLayout将组件放到5各区域,北南东西中,四个位置;
2、 BoxLayout将组件按一行或者一列来排列;
3、CardLayout将组件放到一个区域里,每次只能看到一个组件;
4、FlowLayout将组件从左至右排列,排不下时另起一行;
5、GridLayout将组件放到横纵的格子里;
6、GridBagLayout将组件放到单元格里,允许组件占据多个单元;

  1. 给组件设置边框、颜色、字体;

1、 调用setBorder方法给任意组件设置边框,如:EmptyBorder(组件的四周留有缓冲空间,但没有可视效果)、LineBorder(组件四周有简单的线条)、EtchedBorder(组件四周有蚀刻的效果)、TitleBorder(线框中可以设置标题)等;Border的效果还可以叠加;
2、可以给组件设置前景色和背景色,前者通过setForeground(Color c),后者通过setBackground(Color c);
3、组件中的文件可以通过setFont方法进行设置;通过GraphicsEnvironment.getAvailableFontFamilyNames()获取可用的字体名列表;
4、通过setTooltipText给组件添加提示,当鼠标停留在这个组件上的时候就会显示提示内容;
通过setMnemonic设置助记符,会给标签的字符添加一个下划线,表示他可以用作快捷键;
5、可以通过Box.create方法创建Rigid 和 Glue区域的组件,前者是可以宽高,后者是跟内容区域自动收缩;
6、JComboBox指定一个数组创建组合选择列表;

  1. 事件常用的有鼠标事件MouseEvent、键盘事件KeyEvent类等。当想要监听一个组件的时间时候调用addListener方法设置一个实现了listener接口的类,获取点击时间的回调;

第9章 Java Applet (已过时)

  1. java applet 又叫小程序,虽然也是用java程序编写,但是它必须嵌入到HTML文档中,并在浏览器环境下才能运行; (尝试在Android studio 运行失败)

第10章 java数据流

  1. 输入数据流
  • 只能读不能写;
  • 由抽象类InputStream继承而来;
  • 读数据时,调用read方法,无数据可读时会返回-1;为了提高读取效率,会配合BufferInputStream以系统允许的最大数据块为单位进行读取;
  1. 输出数据流
  • 只能写不能读;
  • 由抽象类OutputStream继承而来;
  • 使用write方法进行写入数据,为了加快数据传输速度,提高数据输出效率,有时输出数据流在提交之前要把所有要输出的数据先锁定在内存缓冲区中,然后再成批的进行输出,每次传输过程都以某特定数据长度为单位进行传输;所以在最后需要调用flush方法将剩余在缓冲区中的数据强制提交;
  1. 文件流,使用FileInputStream和FileOutputStream类进行操作;
  2. 过滤数据流
  • 基本数据流只能提供对字节或者字符的处理,当需要处理其他类型时,需要使用一个过滤器类来包装输入流;
  • 过滤数据流包括缓冲区数据流和数据流等;
  • 缓冲区数据流的作用是在读写数据时,数据会先以块为单位先进入缓冲区,然后直接操作缓冲区即可;BufferedInputStream和BufferedOutputStream,输入和输出;
  • 数据流可以读写java的原始数据包括布尔型、浮点型;DataInputStream 和 DataOutputStream,分别是输入和输出,在创建时通缓冲区数据流一样,需要传一个基本数据流;
    5.基本字符流
  • 跟基本数据流一样,只是字符流是专门处理字符的;由Reader和Writer两个抽象类泛生;
  • InputStreamReader和OutputStreamWriter, 在创建时可以指定字符集编码名称。如: 8859_1;

第11章 线程

  1. 程序每一次执行都对应一个进程,进程是系统进行资源分配和调用的一个独立单位;进程的状态分为:运行、阻塞、就绪3种状态;
  2. 线程是进程执行过程中产生的多条执行线索,线程自身不能运行,必须依赖于某一进程之中,由进程触发执行;线程一共有4中状态:新建、就绪、死亡、阻塞;线层在java.lang包中使用Thread类创建线程;
  3. java的线程中包括3个部分:虚拟CPU、执行的代码、处理的数据;
  4. 创建线程后必须调用start方法启动线程,这时线程会进入就绪状态,排在队列中,等待执行;就绪队列中的线程都在等待CPU,只要CPU一空闲,系统会从就绪队列中挑选一个运行。在挑选时候会根据线程优先级进行挑选执行;线程执行完毕或是在运行中调用了Runtime对象的exit方法就会熬制线程死亡;调用sleep和wait方法会是线程进入阻塞状态; 调用interrupt方法可以中断线程,既可以中断正在运行的线程,也可以中断正在阻塞的线程,中断后会抛出一个InterruptedException异常;
  5. 创建一个线程,创建一个类继承Thread类,重写run方法,将要执行的代码放在该函数中;使用时创建该对象调用start方法;
  6. 还可以通过一个类实现接口Runnable,实现run方法,再创建thread对象传入个类的对象,通过thread对象调用start方法;
class TestRunnable implements Runnable {

        @Override
        public void run() {
            
            System.out.println("hello thread");
        }

    public static void main(String [args]) {

        Thread thread = new Thread(new TestRunnable());
        thread.start();
    }
   }
  1. 线程的调度
  • 在java中线程调度是抢占式,抢占式调用是指可能有多个线程准备运行,但只有一个在真正运行;
  • java线程的调度策略是优先级高的限制性,优先级低的后执行;最大优先级是10,最小是1,默认创建的是5;同优先级的线程会遵循先进先出的原则,给其他同等优先级的线程一个运行的机会,如果没有同等级的线程,就将调用yield的线程放入就绪队列的尾部;
  • 当一个线程被抢占而停止运行或者一个被阻塞的线程就绪后都会放在队列的最后一个;
  • Thread包中提供了yield方法,使处在运行态的线程让出正在占用的CPU,
  • sleep方法允许低优先级的线程运行,而yield方法只给通优先级线程运行的机会;
  • wait方法使线程等待直到,直到收到notify或者notifyAll消息时才被重新激活;
  1. 线程的挂起
  • 就是暂停一个线程,操作的方法只有sleep和join;
  • sleep调用后,CPU会执行其他的线程;
  • join将引起现行的线程等待,知道join所调用的线程执行完成;如:在A线程中用B线程执行join,这时A线程会被阻塞执行B线程执行完成,A线程才会继续执行;
  1. 线程间的通信
  • java中使用管道流连接两个线程,管理导流分为:读管道流(PipedInputStream)和写管道流(PipedOutputStream),一个线程放一个管道流。在创建输入管道流的时候需要传入相关的输出管道流对象;
  • 如果要实现一个单向通信就需要一个第三方类协调管道流到其他的线程中,以达到通信的目的;
PipedOutputStream outputStream = new PipedOutputStream();
PipedInputStream inputStream = new PipedInputStream(outputStream);

第12章 java的网络功能

  1. java中封装的网络库主要是基于TCP/IP 协议,通信时首先需要知道机器的IP地址和端口号。端口号是一个16位整数,取值范围是0165535,其中01023是系统保留并使用的。如http服务端口是80,Telnet服务端口是21,ftp服务的端口号是23等;因此自己在定义端口号时应选择一个大于1023的数作为端口号;
  2. Java是是通过使用流模式来实现网络信息交互的,一个接口同时拥有两个两个流-输入流和输出流;在传输时使用饿TCP和UDP传输协议;
  • 利用TCP协议传输数据时是在端点与端点之间建立持续的连接而进行通信。连接后,发送端将数据加上序列号和错误检测码,并以字节流的方式发送出去;接收端则对收到的数据进行错误检查并按顺序将数据整理好,因此整个字节流到达接收端时完好无缺;
  • 利用UDP协议进行数据传输时,直接将数据定义成数据报(Datagram),在数据报中指定数据索要到达的端点,然后再将数据报发送出去。这种传输方式是无序的,也不用建立连接,所以不是绝对安全可靠的,因此也比较高效;
    网络类中常用的类如下:
所属 类名
面向IP层 InetAddress
面向应用层的类 URL、URLConnection
面向网络层中与TCP相关的类 Socket、ServerSocket
面向网络层中与UDP相关 DatagramPacket、DatagramSocket、MulticastSocket

根据域名获取ip

InetAddress address = null;
        try {

            address =  InetAddress.getByName("www.baidu.com");
        } catch (UnknownHostException e) {

        }
        System.out.println(address);

  1. URL是统一资源定位器的缩写,表示Internet上某一资源的地址;
    读取url的数据
        try {

            URL url = new URL("https://www.baidu.com");

            BufferedReader inputStream = new BufferedReader(new InputStreamReader(url.openStream()));

            String readContent;
            while ((readContent = inputStream.readLine()) != null) {

                System.out.println(readContent);

            }
            inputStream.close();

        }catch (MalformedURLException e) {


        } catch (IOException e) {

        }
  1. Socket 通讯步骤:

(1) 在服务器端指定一个用来等待连接的端口号,在客户端规定一个主机和端口号,从而在客户端和服务器端创建socket和ServerSocket实例;
(2)打开连接到Socket的输入/输出流;
(3) 利用输入输出流按照一定的协议对Socket进行读 写操作;
(4)关闭输入输出流和socket;

class ServerSocketDemo {

    public static void main(String[] args) {

        ServerSocket serverSocket = null;
        Socket socket = null;

        BufferedWriter writer = null;

        try {
            serverSocket = new ServerSocket(3456);

            socket = serverSocket.accept();

            writer = new BufferedWriter(new OutputStreamWriter(socket.getOutputStream()));

            writer.write("Hey guys, welcome to my channel");

            writer.flush();

            writer.close();
            socket.close();


        } catch (IOException e) {


        }
    }

}
class ClientSocketDemo {

    public static void main(String[] args) {

        Socket socket = null;
        BufferedReader reader = null;
        try {
            socket = new Socket("127.0.0.1", 3456);


            reader = new BufferedReader(new InputStreamReader(socket.getInputStream()));


            System.out.println(socket.isConnected() ? "连接成功" : "未连接");
            String response;
            while ((response = reader.readLine()) != null) {

                System.out.println("收到消息:" + response);
            }

            reader.close();

            socket.close();

        } catch (IOException e) {

            System.out.println(e);
        }

    }

}

你可能感兴趣的:(Java 语言程序设计复习笔记)