如果并不知道程序运行时会需要多少对象,或者需要更复杂方式存储对象——可以使用Java集合框架 集合Collection的特点:无序,可重复 列表List的特点:有序(插入顺序),可重复 ArrayList:是List的一个实现类,底层由数组构成 实现了长度可变的数组,在内存中分配连续的空间,遍历元素和随机访问元素的效率比较高 扩容数组时,新数组长度是原来的1.5倍 增:add(值),addAll(集合对象) 删:remove(下标),remove(值),removeAll(集合对象) 改;set(下标,值) 查:三种遍历方式–>1)下标遍历2)增强型for遍历3)迭代器遍历 LinkedList:是List的另一个实现类,底层由链表构成,插入、删除元素时效率比较高 增:add(值),addAll(集合对象),addFirst(值),addLast(值) 删:remove(下标),remove(值),removeAll(集合对象),removeFirst(),removeLast() 改;set(下标,值) 查:三种遍历方式–>1)下标遍历2)增强型for遍历3)迭代器遍历 getLast(),getFirst()
ArrayList和LinkedList的区别: Array查询修改比较快(数组结构),Linked删除和插入比较快(链表结构) Set的特点:无序,不可重复-->往往用来去重-->不够安全 存储一组唯一,无序的对象,Set中存放对象的引用 HashSet:通过哈希码找到数据 打印输出顺序根据hash值来 LinkedHashSet:在HashSet基础上加入链表结构,特点是有序不重复 TreeSet:-->不用了Map的特点:键值对 键不可重复,由且仅可能有一个键的值为null,键的值不建议为null,值可重复 1.8之前,数组加双向链表方式 1.8时,数据总数超过8时,采用红黑树 HashMap:是Map的实现类,通过键生成的hash码来存储值 LinkedHashMap:在HashMap基础上,使之有序 舍弃了红黑树,舍弃了性能,保证了顺序 ConcurrentHashMapL:由于Collection和Map都不满足多线程的设定,java原本提供的HashTable这个类不满足开发要求,所以又提供了这样一个类来解决多线程并发的问题 TreeMap:–>不用了 迭代器遍历步骤 1.获取Iterator :Collection 接口的iterator()方法 2.获取对象 Iterator的方法 boolean hasNext(): 判断是否存在另一个可访问的元素 Object next(): 返回要访问的下一个元素 while(iterator.hasNext()){ iterator.next(); } 泛型 JDK5.0使用泛型改写了集合框架中的所有接口和类 将对象的类型作为参数,指定到其他类或者方法上,从而保证类型转换的安全性和稳定性 示例:List list = new ArrayList(); 泛型中的通配符 T(type)–>具体java类型 E(element)–>代表元素 K(key)–>键 V(value)–>值 ?–>不确定的java类型 Collections集合工具类 实现自定义排序 1.实现Comparable接口 2.重写compareTo()方法,定义对象比较规则–>按照学号 public int compareTo(Object o) { Student student =(Student)o; if(this.getId()==student.getId()){ return 0; //0时相等 }else if(this.getId()>student.getId()){ return 1; //正数当前值比参数大 }else { return -1; //负数当前值比参数小 } } 3.调用sort()时底层会调用compareTo()这个方法 自定义排序后二分查找 1.实现Comparable接口并添加本类泛型 2.重写compareTo()方法 3.sort()然后再二分查找
枚举–>enum关键字定义,枚举指由一组固定的常量组成的类型可看作一个特定的集合 定义: 修饰符 enum 类名{ 值 } 内容是常量(直接是值,不需要其他符号) 枚举类型的值判断只要用双等号(valueOf) 包装类 包装类并不是用来取代基本数据类型的,在基本数据类型需要用对象表示时使用 装箱:基本类型–>包装类型 拆箱:包装类型–>基本类型 Boolean类构造方法参数为String类型时,若该字符串内容为true(不考虑大小写),则该Boolean对象表示true,否则表示false 当Number包装类构造方法参数为String 类型时,字符串不能为null,且该字符串必须可解析为相应的基本数据类型的数据,否则编译不通过,运行时会抛出NumberFormatException异常 parseXXX():把字符串转换为相应的基本数据类型数据(Character除外)(字符串->基本类型) valueOf(type value):所有包装类都有此方法(基本类型->包装类) 除Character类外,其他包装类都有如下方法(字符串->包装类)valueOf(String s)
String 常用方法 length() equals split() public int indexOf(int ch) 搜索第一个出现的字符ch(或字符串value),如果没有找到,返回-1 public int indexOf(String value) public int lastIndexOf(int ch) 搜索最后一个出现的字符ch(或字符串value),如果没有找到,返回-1 public int lastIndexOf(String value) public String substring(int index) 提取从位置索引开始的字符串部分(包括该位置) public String substring(int beginindex, int endindex) 提取beginindex和endindex之间的字符串部分(左闭右开) public String trim() 返回一个前后不含任何空格的调用字符串的副本 字符串连接 方法1:使用“+” 方法2:使用String类的concat()方法 String是不可变的字符串,最安全,但速度最慢 StringBuffer和StringBulider都是可变的字符串类型 StringBuilder是单线程,不安全,但速度快–>常用方法apend(),toString(); StringBuffer是多线程,安全,但速度慢 Date //创建日期对象 Date date = new Date(); //定制日期格式 SimpleDateFormat formater = new SimpleDateFormat(“yyyy- MM-dd HH:mm:ss”); String now = formater.format(date); System.out.println(now); Calender Calendar calendar = Calendar.getInstance();//抽象类获取对象 System.out.println(calendar.get(Calendar.YEAR)); //月份下标是从0开始,需要+1 System.out.println(calendar.get(Calendar.MONTH)+1); System.out.println(calendar.get(Calendar.DAY_OF_MONTH)); //星期天是第一天,需要-1 System.out.println(calendar.get(Calendar.DAY_OF_WEEK)-1);
IO流按流向分类: 输入: 基类:InputStream Reader FileInputStream FileReader 输出: 基类:OutputStream Writer FileOutputStream FileWriter 按编码分类: 字节流:OutputStream InputStream 字符流:Writer Reader 高级流: 增强流:(有缓冲区提高效率) BufferedReader BufferedWriter 转换流:(从字节流转成字符流,可以设置字符编码格式) InputStreamReader OutputStreamWriter 二进制流:(把字节流包装成二进制流) DataInputStream DataOutputStream 对象流:(序列化与反序列化) ObjectInputStream ObjectOutputStream
进程与线程 进程:系统执行程序的任务,有分配好的内存和cpu资源可以调用 线程:系统执行程序的任务,cpu执行任务的最小命令单元 线程的状态: 创建 就绪 start 运行中 run 阻塞 销毁 创建线程的两种方式 1)继承Thread类 创建类继承Thread类 重写run()方法 创建该线程对象,调用start()方法启动线程 特点: 编写简单,可直接操作线程 适用于单继承 2)实现Runnable接口–>实际中该方法用的更多 创建类实现Runnable接口 重写run方法 将该类包装成一个Thread类线程对象 调用start()方法启动线程 特点: 避免单继承局限性 便于共享资源 线程调度 setPriority(int newPriority) 设置线程优先级 -->只是可能性高低不是绝对的 sleep(long millis) 线程休眠参数为毫秒数 join() 暂停其他线程,强制当前线程运行 interrupt() 线程中断 yield() 线程礼让,只是一种可能性–>感觉没啥用处 线程同步–>关键字synchronized 两种方式 1)修饰代码块 synchronized(this){} 2)修饰方法 特点: 同一时刻只能有一个线程进入synchronized(this)同步代码块 当一个线程访问一个synchronized(this)同步代码块时,其他synchronized(this)同步代码块同样被锁定 当一个线程访问一个synchronized(this)同步代码块时,其他线程可以访问该资源的非synchronized(this)同步代码
网络 ipconfig查看网络地址(windows系统) ping测试网络是否通畅(windows系统)
Socket C/S:client/server 客户端 B/S:browser/server网页 交互过程: Server端开放端口 ServerSocket ss=new ServerSocket(6000); server段监听端口 Socket s=s = ss.accept(); client端连接server端端口 Socket s = new Socket(“127.0.0.1”,6000); client端获取输出流–在输出流中写入数据 OutputStream os = s.getOutputStream(); os.write(String s); server端监听到client端的数据传输,server端获取输入流–读取输入流的数据 InputStream is = s.getInputStream(); StringBuffer sb = new StringBuffer(); int temp; while((temp=is.read())!=-1){ sb.append((char)temp); } rst =sb.toString(); 依次关闭client端和server的流和socket对象
定义:反射是指在程序运行期间,能够观察和修改类或者类的对象的属性和行为的特性 反射获取类的3种方式: --c 1)Class.forName(“全类名”); 2)类型.class; 3)对象.getClasss(); 无参构造: Constructor con = c.getConstructor(); //公共的 Constructor con = c.getDeclaredConstructor();//非公共的 con.setAccessible(true);//修改权限 Object obj= con.newInstance();//获取对象 有参构造: Constructor con = c.getDeclaredConstructor(int.class … 参数类型列表); con.setAccessible(true);//修改权限 Object obj= con.newInstance(对应的值列表);//获取对象 普通方法: Method m = c.getDeclaredMethod(“setSex”,String.class);//第一个参数时方法名,第二个是方法的参数类型列表 m.setAccessible(true);//修改权限 m.invoke(stu,“母”);//第一个参数是对象,第二个是参数值列表 该方法的返回值由对应的方法决定 属性: Field[] fields = c.getDeclaredFields();//获取全部属性 遍历可以获取访问修饰符 属性类型 属性名 可以再遍历过程中设置 field.setAccessible(true);修改权限 可以使用field.set(对象,属性值);来进行赋值 for (Field field : fields) { field.setAccessible(true); if(field.getName().equals(“id”)){ //需要建对象才能对属性赋值 field.setInt(s,1); }else if(field.getName().equals(“name”)){ field.set(s,“王小虎”); } }