Java基础知识总结

JDK(Java Developer's Kit): Java开发人员工具包。

抽象类:用abstract修饰的类,抽象类不能被实例化,即不能new成一个对象。

抽象方法:abstract修饰的方法。仅有方法申明,而没有方法体的方法(没有{},若有{}但里面是空的,这也算实现了,叫做空实现)。 抽象类中并不一定要全是抽象方法,也可以写实现方法。

或者可以说:包含抽象方法的类就叫抽象类。如果一个类中包含一个或多个抽象方法,那这个类就是抽象类。

接口(interface):一种特殊的抽象类,所有方法都是抽象的。 定义类的规范, 实现该接口的类便要遵守接口所定的规则。 接口中定义的的变量必须初始化,默认类型为public static final(也就是常量了),接口中的方法都是抽象方法,默认类型为public abstract。

接口可以继承另一个接口,但接口不能实现另一个接口。 一个类可以实现多个接口,但只能继承一个类。(多实现,单继承)

接口和抽象类的区别:接口是特殊的抽象类,抽象类中的方法并不一定全是抽象方法,而接口中的方法一定得是抽象的。 接口不可以实例化。

抽象类和接口的异同:

 都是一种抽象的约束,或者说规范。

 都不能实例化。

 里面都可以放抽象方法。不过接口要求必须全是抽象方法。

 抽象类的本质是类,它只能被单继承;而接口可以被多实现(一个类可以实现多个接口)

switch(integral-selector) 
{
    case integral-value1 : 
                 statement1;    
                 break;     
    case integral-value2 :    
                 statement2;
                 break; 
    case integral-value3 :    
                 statement3;    
                 break;    
                
                 ....     
    default :
                 statemet;  

}

多态:

   父类型的引用可以指向子类型的对象。例如: People stu = new Student();
   多态是一种运行期行为,不是编译期行为。
   当使用多态方式调用方法时,首先检查父类中是否有该方法,如果没有,则编译错误;如果有,再去调用子类的该同名方法。

向上转型:Student当然也是People类型的,(乌鸦一定是鸟类,动物,生物) People stu = new Student();

向下转型:(要强制类型转换) People stu = new Student(); Student stu1 = (Student)stu;

final : 终态。表示固定的形态,不能被修改扩展。

当它修饰类时,表示该类不能被继承拓展; 修饰方法时,表示该方法不能被子类中的方法覆盖(重写); 修饰变量时,表示常量。

static关键字:
  一般情况下在一个类中,每创建一个对象Java就会在内存中为每个对象单独分配一块存储空间,该空间内有该对象特有的字段值和方法;
但是如果字段或方法前有static关键字,则表示该字段和方法是属于整个类公有的,Java会分配一块“公共区域”来存储这些字段和方法。
因此可以直接通过类调用这些方法:XXXClass.xxxMethod();

static方法中不能调用非静态方法!!!为什么?理解不了。。。。

return关键字的作用:

  1.表示方法已经结束,退出此方法;

  2.如果此方法产生了一个值,则将它带出方法,传递出去。

  如果方法返回类型为void,则程序员不必手写return,因为其实在该方法的结尾处有个隐藏的return null。此时return的作用只是退出此方法。

String类 :

  String是常量,其对象一旦创建就不能被改变。那些看起来会修改String值的方法,其实都是创建了一个全新的String。

  String通过+可以拼接其他东西,并默默地把人家的数据类型转换为String类型,拼接后的String是一个全新的String对象。

  字符串里的+表示前后字符串连接,若一个不是字符串,那它会自动被转换为字符串,然后进行字符串连接。
  例如: System.out.println("abc"+123);123原本是int型的,但在此会被转换成String,然后连接成新字符串"abc123"。

  StringBuffer和String的主要区别就是StringBuffer创建的对象的值可以改变,而String的对象的值一旦创建便不能再变。

String和StringBuffer的相互转换:

  需要注意的是String和StringBuffer属于不同的类型,没有继承关系,所以不能强制类型转换。他们之间转换必须如下:

      String str1  = "abc";

      StringBuffer strbuf1 = new StringBuffer(str); // String类型转换为StringBuffer

      StringBuffer strbuf2 = new StringBuffer("def");

      String str2 = strbuf2.toString();  // StringBuffer类型钻换为String

字符串对象的两种创建方式:

  String str1 = new String("aaa");

  String str2 = new String("aaa");  

这是两个对象,只要new,就会创建一个对象。 

   String str1 = "aaa";

   String str2 = "aaa";

同一个对象。 具体解释见:http://www.cnblogs.com/mengdd/archive/2013/01/03/2842846.html    

数组(Array):相同数据类型的集合。

定义数组的几种方式: int[] array = new int[10];   int array[] = new int[10];    int[] a = {1,2,3,4};   int[] a = new int[]{1,2,3,4};

容器/集合(collection):容器的用途就是保存对象。集合中不能存放基本类型的数据,要存它的包装类的对象,即集合中只能存放对象。

 以前,编译器的数据类型是Object,当插入对象时,无论对象的类型是什么都是没问题的,但是当get时,它对所有对象的返回类型都是Object,显然,这样是有问题的。

 为了避免出现这样的错误,我们可以用尖括号里规定该集合存储的特定数据类型。List<String>

   List<String> lst = new ArrayList<String>();
   本来new的是ArrayList类型的对象,但前面的类型却为List,但lst对象运行时他却能调用自己的方法,我们已经知道这便是Java的多态。
   但这样写必须满足:lst调用的方法必须是List接口中有的。
     它先会从父类或接口中查找调用的方法,若存在,则就会调用子类中覆盖的此方法。若父类中不存在lst调用的方法,则会报错。

  List集合是有序集合,集合中的元素可以重复,访问集合中的元素可以根据元素的索引来访问。

    ArrayList

         ArrayList的底层数据结构是数组,执行查询操作效率较高;如果ArrayList插入或删除一条数据,那么该数据插入点或删除点后的数据都要移动,低效率。

         非同步,如果多个线程同时访问一个ArrayList,则需自己同步。     

         数组和ArrayList的区别: 集合(ArrayList)只能保存对象,而数组既能保存基本类型的数据也能保存对象;数组的大小是固定的,而ArrayList没有固定大小

    LinkedList:

         LinkedList的底层数据结构是双链表,插入,删除效率很高。

         非同步。

    Vector:

         与ArrayList类似,但Vector是线程同步的。但一般操作效率没ArrayList高。

  Set集合是无序集合,集合中的元素不可以重复,访问集合中的元素只能根据元素本身来访问。

    HashSet:

        HashSet的底层数据结构是HashMap,value的值都是统一的,而HashSet的值是存储在key里的,这也就是Set里元素不能重复的根本原因,因为Map里key不能重复。

        LinkedHashSet:HashSet的一个子类,链表

    SortSet(接口):

        TreeSet: 把放入集合中的元素按一定顺序排列。加入集合的元素必须是可比较的,不然加第二个元素时就会报错:ClassCastException异常

  

  Map集合中保存(key,value)对形式的元素,key不能重复,若添加已经存在的key,不会报错但会覆盖原来的(key,vlaue),Map的添加方法叫put(K key,V vlaue)。

    HashMap:

        我们已经知道HashSet的底层数据结构是HashMap。而HashMap的底层数据结构是什么呢?

        HashMap的底层维护一个数组,我们向HashMap中所放的对象实际上是存储在该数组中。

        当向HashMap中put(key,value)一对键值对时,它会根据key的hashCode值计算出一个位置,位置就是此对象准备往数组中存放的位置。

两种遍历集合的方式:

   Iterator:迭代器。首先集合获取一个迭代器,然后迭代器里通常用hasNext(),next() 

   foreach:

Collection和Collections的区别:

    Collection是Java集合的顶级接口,接口List和Set都实现了它。

    而Collections是针对于Java集合的帮助类。它提供一系列静态方法对各种集合进行各种操作。

泛型:所谓泛型,就是变量类型的参数化,由程序员指定集合只能容纳的数据类型。

 以前,编译器的数据类型是Object,当插入对象时,无论对象的类型是什么都是没问题的,但是当get时,它对所有对象的返回类型都是Object,显然,这样是有问题的。 为了避免出现这样的错误,我们可以用尖括号里规定该集合存储的特定数据类型。List<String>

通过使用泛型,就可以防止在编译器将错误类型的对象放入容器里。

 有关泛型博客:http://www.cnblogs.com/mengdd/archive/2013/01/21/2869778.html

包装类 :8种基本数据类型,不是对象。为此Java里定义了8个对应的包装类,他们可以作为对象使用。

自动装箱和自动拆箱:

  自动装箱:基本数据类型自动转换为包装类型;

  自动拆箱:包装类型自动转换为基本数据类型。         

Java的反射机制:

   动态的(运行时)获取类的信息以及动态调用对象的方法的功能。  

   要想使用反射,首先需要获得待操作的类所对应的Class对象。

  Java中,无论生成某个类的多少个对象,这些对象都会对应于同一个Class对象。

  这个Class对象是由JVM生成的,通过它能够获悉整个类的结构。

获取Class对象常用的三种方法:  

  1.使用Class类的静态方法: Class.forName("。。。。");  

  2.使用对象的getClass()方法 : 对象.getClass();

  3.使用类的.class语法 : String.class;  

Class类 :   每个类在开始运行时,Class类都会通过类加载器生成一个该类的Class对象,里面存储了该类的信息。

Java IO流 :

  根据处理数据类型的不同:字节流、字符流。字节流:InputStream,OutputStream 俩抽象类及下的子类。字符流:Reader,Writer 俩抽象类及以下的子类。

  根据数据流向不同:输入流、输出流

  字节流和字符流的区别:

    读写单位不同:字节流以字节为读写单位,字符流以字符为读写单位,可能是多个字节。

    处理对象不同:字节流能处理所有类型的数据(包括图片、avi),字符流只能处理字符类型的数据。只要是处理处文本数据,就优先考虑字符流,除此之外都使用字节流 。

  装饰流:

  File类:

Java对象序列化:将对象转换成字节流保存起来,并在以后再转换还原成对象,就成为对象序列化;只有实现了Serializable接口的类的对象才能序列化。

对象持久化:把对象保存到永久存储设备上称为持久化。

Java基本数据类型:
  Java中有8种基本数据类型:byte, char, short, int, float, long, double, boolean
    但基本类型不是对象,所以Java对应的有8个包装类:Byte, Character, Short, Integer, Float, Long, Double, Boolean
  
    1 char = 2 byte       1 short = 2 byte
    1 int = 4 byte        1 float = 4 byte
    1 long = 8 byte    1 double = 8 byte
   
    1 byte = 8 bit(1字节 = 8位)
   
     基本数据类型自动转换成包装类型叫自动装箱;反之,叫自动拆箱。
 
 高精度数字:用于表示金额等。BigIntegerBigDecimal

  

操作符:

  一元加,减操作符:
    自动递增递减:(前缀式和后缀式)
       ++a :先运算,后生成值;
       a++ : 先生成值,后运算。
 
      关系操作符:关系操作符生成的是一个boolean结果。
     ==和equals()方法的比较:
      其实equals()的默认行为是比较引用,若返回true,则表示它们指向同一个地址,即同一个对象。此时,==和equals()作用是一样的。
         但如果在自己的类中覆盖了equals()方法,则equals()方法只表示比较两对象的值(内容)是否相等。

   逻辑操作符:与(&&),或(||),非(!)。能根据参数的逻辑关系,生成一个boolean值(true/false)。
  
   指数计数法:Java中的e=10,并不是2.718。
 
   按位操作符:
 
   移位操作符:
 
   三元操作符:boolean-exp ? value1 : value2; 它表示如果布尔表达式为真,则执行value1,若为假,则执行value2。
   三元操作符的作用其实等价于if...else...语句,但它更简洁高效,不过它可读性差。

数据类型转换:

  扩展转换:比如float a = 12;当将int型数据12赋值给float类型的a时,编译器会自动的把12转换成为float型的。这就叫扩展转换,也叫类型提升,类型提升是安全的。
     窄化转换:会出现数据装不下而丢失信息的情况,所以窄化转换是不安全的,如果非要转换,则要强制转换。

Java中没有sizeof():

   在C和C++中,不同的数据类型在不同的机器上可能有不同的大小,C程序员必须通过sizeof()得知机器为那些数据类型分配的字节数。

  而Java不存在这个问题,因为所有数据类型在不同的机器上大小是相同的。 

迭代:for循环和foreach()的区别:

break 和 continue的区别:  

  break: 强行退出循环,不执行循环中剩余的语句。

  continue: 停止本次循环,退回循环起始位置开始下一次循环。

   

switch: 根据括号里整型表达式的值,执行相应的代码后,因为有break,所以会跳出该循环。但如果没有找到一项对应,则会执行default默认的代码。

   注意:括号里的值必须为整型的 

switch(integral-selector) 
{
    case integral-value1 : 
                 statement1;    
                 break;     
    case integral-value2 :    
                 statement2;
                 break; 
    case integral-value3 :    
                 statement3;    
                 break;    
                
                 ....     
    default :
                 statemet;  

}

初始化与清理:

  构造器/构造函数:   构造函数名与类名一致;  

    在类被加载时,就执行构造函数;  

    构造函数可以是无参的,也可以是有参数的  

    每个类都默认有个无参的构造函数,而若想在对象初始化时传入参数,就得自己手写有参数的构造函数了。当自己手写了有参数的构造函数后,默认的无参构造函数就不存在了。     

  清理:   C中析构函数的概念??????   

      finalize()方法: 

重载:  几个重载的方法:方法名相同,参数不同(哪怕只是参数列表顺序不同),返回值可能不同。      

成员初始化:  Java尽力保证所有变量在使用前都能得到恰当的初始化。

    对于基本类型的全局变量如果程序员没有初始化,则编译器会有默认自动初始化值;而方法内的局部变量则会报错,提醒程序员自己初始化。

   如果你没手动初始化,编译器可能会为你自动初始化; 例:int a; 编译器会自动为a赋值0,即a的默认值是0  当然你也可以手动为成员赋值; 例: int a = 5;  把5赋给a  除此外,你也可以通过构造函数初始化

Java访问权限修饰符:

  private : 只有本类内部才可以访问。   

  frindly(默认空) : 包访问权限。同一个包里的类之间可以互相访问。

  protected : 继承访问权限。被它修饰后,不同包间只有继承了它的类可以访问,同一个包内,  

  public :公开的。

绑定: 将方法调用和方法主体关联起来。

   前期绑定:在程序执行前绑定。

   后期绑定:(动态绑定或运行时绑定)在程序运行时根据对象类型绑定。而它是根据Java的反射机制来判断对象的运行时类型的。      

多态:    

策略设计模式:

适配器设计模式:


 

原文地址:https://www.cnblogs.com/wangerxiansheng/p/4088961.html