Java_基础知识回顾

1、ByteArrayInputStream、 ByteArrayOutputStream

  1. String str = "ZHANGSAN";
  2. //System.out.println(str.toLowerCase());
  3. ByteArrayInputStream inputStream = new ByteArrayInputStream(str.getBytes());
  4. ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
  5. int b;
  6. while((b = inputStream.read()) != -1){
  7. char lowerCase = Character.toLowerCase((char)b);
  8. outputStream.write(lowerCase);
  9. }
  10. byte[] lowerCases = outputStream.toByteArray();
  11. System.out.println(new String(lowerCases,0, lowerCases.length));

全部在内存中完成byte的转换

2、PrintStream:向目标打印

属于OutputStream的实现类,向目标(可能是文件、标准输出屏幕、输出流、网络等)打印各种样式,不过比一般的输出提供了更多的打印方式,可以打印各种数据类型和样式等

  1. OutputStream outputStream = System.out;
  2. outputStream.write("helloABC张三".getBytes());
  3. outputStream.close();

列出当前操作系统的系统参数,输出到文件中

  1. PrintStream printStream = new PrintStream("hello.txt");
  2. System.getProperties().list(printStream); 
  3. printStream.close();

3、InputStreamReader、OutputStreamWriter, 计算机存储都是字节流的形式,而读取到内存中需要识别一个个的字符(人只能识别字符),有可能1个字节就代表一个字符(例如英文),也有可能多个字节才能转换成一个字符(例如中文),如果中间存在丢失或无法转换,则看到的就是一堆?

InputStreamReader:将输入的内容字节变成字符

OutputStreamWriter:将输出的内容从字符变成字节

4、合并流:SequenceInputStream

  1. File file1 = new File("hello.txt");
  2. File file2 = new File("test.txt");
  3. InputStream inputStream1 = new FileInputStream(file1);
  4. InputStream inputStream2 = new FileInputStream(file2);
  5. SequenceInputStream sequenceInputStream = new SequenceInputStream(inputStream1,
  6. inputStream2);
  7. BufferedInputStream bufferedInputStream = new BufferedInputStream(sequenceInputStream);
  8. int c;
  9. while((c = bufferedInputStream.read()) != -1){
  10. System.out.print((char)c);
  11. }
  12. bufferedInputStream.close();
  13. sequenceInputStream.close();
  14. inputStream1.close();
  15. inputStream2.close();

测试结果:helloworld

在实验中,从bufferedInputStream去取到两个文件大小相加的byte数组中,代码如下,转换出来有问题,有点奇怪,只读到了前一个流中的内容,后面一个流中的内容没读取进来。思考中...

  1. File file1 = new File("hello.txt");
  2. File file2 = new File("test.txt");
  3. InputStream inputStream1 = new FileInputStream(file1);
  4. InputStream inputStream2 = new FileInputStream(file2);
  5. SequenceInputStream sequenceInputStream = new SequenceInputStream(inputStream1,
  6. inputStream2);
  7. BufferedInputStream bufferedInputStream = new BufferedInputStream(sequenceInputStream);
  8. int length = (int) (file1.length() + file2.length());
  9. byte[] b = new byte[length];
  10. bufferedInputStream.read(b, 0, length);
  11. System.out.println(new String(b,0,length));
  12. bufferedInputStream.close();
  13. sequenceInputStream.close();
  14. inputStream1.close();
  15. inputStream2.close();

测试结果如下:hello

5、Zip压缩与解压

压缩程序:

  1. ZipOutputStream zipOutputStream = new ZipOutputStream(new FileOutputStream("hello.zip"));
  2. zipOutputStream.setLevel(9);
  3. ZipEntry zipEntry = new ZipEntry("a.txt");
  4. zipOutputStream.putNextEntry(zipEntry);
  5. BufferedInputStream bufferedInputStream = new BufferedInputStream(new FileInputStream("test.txt"));
  6. int content;
  7. while((content = bufferedInputStream.read()) != -1){
  8. zipOutputStream.write(content);
  9. }
  10. bufferedInputStream.close();
  11. zipOutputStream.closeEntry();
  12. zipOutputStream.flush();
  13. zipOutputStream.close();

解压程序:

  1. ZipInputStream zipInputStream = new ZipInputStream(new FileInputStream("hello.zip"));
  2. ZipEntry zipEntry = null;
  3. while ((zipEntry = zipInputStream.getNextEntry()) != null) {
  4. BufferedOutputStream bufferedOutputStream = new BufferedOutputStream(
  5. new FileOutputStream(zipEntry.getName()));
  6. int content = 0;
  7. while((content = zipInputStream.read()) != -1){
  8. bufferedOutputStream.write(content);
  9. }
  10. bufferedOutputStream.flush();
  11. bufferedOutputStream.close();
  12. }
  13. zipInputStream.close();

6、zip压缩某目录下的所有文件及子文件

  1. public void zipDirectory(File pathname, ZipOutputStream zipOutputStream) throws Exception {
  2. if (!pathname.isDirectory()) {
  3. return;
  4. }
  5. File[] files = pathname.listFiles();
  6. for (File file : files) {
  7. if (file.isDirectory()) {
  8. zipDirectory(file, zipOutputStream);
  9. } else {
  10. ZipEntry zipEntry = new ZipEntry(pathname.getName() + File.separator
  11. + file.getName());
  12. zipOutputStream.putNextEntry(zipEntry);
  13. BufferedInputStream bufferedInputStream = new BufferedInputStream(
  14. new FileInputStream(file));
  15. int i;
  16. while ((i = bufferedInputStream.read()) != -1) {
  17. zipOutputStream.write(i);
  18. }
  19. bufferedInputStream.close();
  20. zipOutputStream.flush();
  21. zipOutputStream.closeEntry();
  22. }
  23. }
  24. }

问题:中文编码存在问题,建议选用import org.apache.tools.zip.ZipEntry;

import org.apache.tools.zip.ZipOutputStream,由于其存在方法out.setEncoding("gbk");//指定编码为gbk

6、ThreadLocal

  1. final ThreadLocal<String> threadLocal = new ThreadLocal<String>();
  2. threadLocal.set("main--");
  3. Thread thread = new Thread() {
  4. @Override
  5. public void run() {
  6. threadLocal.set("thread--");
  7. Thread.yield();
  8. System.out.println(Thread.currentThread().getName() + ":" + threadLocal.get());
  9. }
  10. };
  11. thread.start();
  12. Thread.yield();
  13. System.out.println(Thread.currentThread().getName() + ":" + threadLocal.get());

7、数组和List之间的转换

数组->List: Arrays.asList(a)

List->数组:list.toArray()

8、正则表达式

(1)^:在[]内表示取反,在外面表示开头

(2)group

  1. String regex = "[a-z]{3,5}";
  2. Pattern pattern = Pattern.compile(regex, Pattern.CASE_INSENSITIVE);
  3. Matcher matcher = pattern.matcher("Abc_defgh_aa_ABCD1");
  4. while (matcher.find()) {
  5. System.out.print("位置[左闭右开区间):"+matcher.start() + "_" + matcher.end() + ", 匹配内容:");
  6. System.out.println(matcher.group());
  7. }

测试结果:

  1. 位置[左闭右开区间):0_3, 匹配内容:Abc
  2. 位置[左闭右开区间):4_9, 匹配内容:defgh
  3. 位置[左闭右开区间):13_17, 匹配内容:ABCD

(3)邮件的正则表达式

[\\w[_.]][email protected][\\w[_.]]+\\.[\\w]+

(4)"."点号在正则表达式中表示任何字符, 需要表示点号的时候必须转义\\.

(5)group的分组

分组是以正则表达式中的小括号‘()‘为标准的,当匹配成功后,group或group(0)表示匹配的整个字符串,group(1)代表正则中第一个小括号匹配到的内容,group(2)代表第二个小括号代表的内容,依次类推

(6)匹配require引入文件

"^[\\s]*#require[\\s]*\\(\"([\\w./]+)\"\\)[\\s]*$"含义为:以任意空白字符开头,在#require,再任意空白字符,再(",再任意字母、点号、斜线, 再"),最后任意个空白字符结尾

测试代码:

  1. public static void main(String[] args) {
  2. FileInputStream fileInputStream = null;
  3. try {
  4. fileInputStream = new FileInputStream(new File(
  5. "C:/Documents and Settings/***/My Documents/tmp/hello.js"));
  6. } catch (FileNotFoundException e) {
  7. e.printStackTrace();
  8. }
  9. InputStreamReader inputStreamReader = new InputStreamReader(fileInputStream,
  10. Charset.defaultCharset());
  11. BufferedReader bufferedReader = new BufferedReader(inputStreamReader);
  12. String line = "";
  13. try {
  14. while ((line = bufferedReader.readLine()) != null) {
  15. String requireFile = getRequireFile(line);
  16. System.out.println(requireFile);
  17. }
  18. } catch (IOException e) {
  19. e.printStackTrace();
  20. } finally {
  21. try {
  22. bufferedReader.close();
  23. inputStreamReader.close();
  24. fileInputStream.close();
  25. } catch (IOException e) {
  26. e.printStackTrace();
  27. }
  28. }
  29. }
  30. private static String getRequireFile(String line) {
  31. String requireFile = "";
  32. Pattern pattern = Pattern
  33. .compile("^[\\s]*#require[\\s]*\\(\"([\\w./]+)\"\\)[\\s]*$", Pattern.MULTILINE);
  34. Matcher matcher = pattern.matcher(line);
  35. while (matcher.find()) {
  36. requireFile = matcher.group(1);
  37. }
  38. return requireFile;
  39. }

测试文件内容:

  1. var param;
  2. #require("hello/world_util/alibaba123_utils.js")
  3. #require("/abc/world_util/alibaba12666_utils.js")

测试结果

  1. hello/world_util/alibaba123_utils.js
  2. /abc/world_util/alibaba12666_utils.js

9、FileReader有待完备的地方,只能使用系统默认的字符集,而没有提供传递字符集的构造函数

FileReader继承了InputStreamReader,但并没有实现父类中带字符集参数的构造函数,所以
FileReader只能按系统默认的字符集来解码

10、阻塞队列:BlockingQueue

生产者中的 put() 操作会在没有空间可用时阻塞,而消费者的 take() 操作会在队列中没有任何东西时阻塞。

11、信号量:Semaphore, 允许规定数量的线程进入操作,释放之后其他进入执行

  1. Runnable limitedCall = new Runnable() {
  2. final Random    rand      = new Random();
  3. final Semaphore available = new Semaphore(3);
  4. int             count     = 0;
  5. public void run() {
  6. int time = rand.nextInt(15);
  7. int num = count++;
  8. try {
  9. available.acquire();
  10. System.out.println("Executing " + "long-running action for " + time
  11. + " seconds... #" + num);
  12. Thread.sleep(time * 1000);
  13. System.out.println("Done with #" + num + "!");
  14. available.release();
  15. } catch (InterruptedException intEx) {
  16. intEx.printStackTrace();
  17. }
  18. }
  19. };
  20. for (int i = 0; i < 10; i++)
  21. new Thread(limitedCall).start();

12、死锁

  1. public class Demo06 {
  2. public static void main(String[] args) {
  3. DeadLock deadLock1 = new DeadLock();
  4. DeadLock deadLock2 = new DeadLock();
  5. deadLock1.setFlag(true);
  6. deadLock2.setFlag(false);
  7. new Thread(deadLock1).start();
  8. new Thread(deadLock2).start();
  9. }
  10. }
  11. class DeadLock implements Runnable {
  12. private boolean flag = false;
  13. public boolean isFlag() {
  14. return flag;
  15. }
  16. public void setFlag(boolean flag) {
  17. this.flag = flag;
  18. }
  19. private static Object object1 = new Object();
  20. private static Object object2 = new Object();
  21. public void run() {
  22. if (flag) {
  23. synchronized (object1) {
  24. System.out.println(Thread.currentThread().getName() + " get object1.");
  25. try {
  26. Thread.sleep(1000);
  27. } catch (InterruptedException e) {
  28. e.printStackTrace();
  29. }
  30. synchronized (object2) {
  31. System.out.println(Thread.currentThread().getName() + " get object2.");
  32. }
  33. }
  34. } else {
  35. synchronized (object2) {
  36. System.out.println(Thread.currentThread().getName() + " get object2.");
  37. try {
  38. Thread.sleep(1000);
  39. } catch (InterruptedException e) {
  40. e.printStackTrace();
  41. }
  42. synchronized (object1) {
  43. System.out.println(Thread.currentThread().getName() + " get object1.");
  44. }
  45. }
  46. }
  47. }
  48. }

13、反射:通过classloader加载类,标准做法如下:

  1. ClassLoader cl = Thread.currentThread().getContextClassLoader();
  2. if (cl == null) cl = MyClass.class.getClassLoader(); // fallback
  3. Class clazz = cl.loadClass(name);

14、文件大小限制

错误做法:

  1. public int getFileSize(File f) {
  2. long l = f.length();
  3. return (int) l;
  4. }

正确做法如下:

不支持传递超过2GB的文件. 最好的做法是对长度进行检查, 溢出时抛出异常

  1. public int getFileSize(File f) {
  2. long l = f.length();
  3. if (l > Integer.MAX_VALUE) throw new IllegalStateException("int overflow");
  4. return (int) l;
  5. }

15、线程sleep中断

  1. try {
  2. Thread.sleep(1000);
  3. } catch (InterruptedException e) {
  4. Thread.currentThread().interrupt();
  5. }
  6. or
  7. while (true) {
  8. if (Thread.currentThread().isInterrupted()) break;
  9. }

16、开发中常用术语解释

java的几种对象(PO,VO,DAO,BO,POJO)解释  
   一、PO:persistant object 持久对象,可以看成是与数据库中的表相映射的java对象。最简单的PO就是对应数据库中某个表中的一条记录,多个记录可以用PO的集合。PO中应该不包含任何对数据库的操作。

二、VO:value object值对象。通常用于业务层之间的数据传递,和PO一样也是仅仅包含数据而已。但应是抽象出的业务对象,可以和表对应,也可以不,这根据业务的需要.个人觉得同DTO(数据传输对象),在web上传递。

三、DAO:data access object 数据访问对象,此对象用于访问数据库。通常和PO结合使用,DAO中包含了各种数据库的操作方法。通过它的方法,结合PO对数据库进行相关的操作。

四、BO:business object 业务对象,封装业务逻辑的java对象,通过调用DAO方法,结合PO,VO进行业务操作。

五、POJO:plain ordinary java object 简单无规则java对象,我个人觉得它和其他不是一个层面上的东西,VO和PO应该都属于它。

17、多线售票系统:

  1. class TicketSeller implements Runnable {
  2. private int ticketCount = 10;
  3. @Override
  4. public void run() {
  5. while (ticketCount > 0) {
  6. synchronized (this) {
  7. if (ticketCount > 0) {
  8. try {
  9. Thread.sleep(100);
  10. } catch (InterruptedException e) {
  11. e.printStackTrace();
  12. }
  13. System.out.println(Thread.currentThread().getName()
  14. + " sell ticket: " + ticketCount--);
  15. }
  16. }
  17. }
  18. }
  19. }
  20. public class Demo01 {
  21. public static void main(String[] args) {
  22. TicketSeller ticketSeller = new TicketSeller();
  23. new Thread(ticketSeller, "Thread A").start();
  24. new Thread(ticketSeller, "Thread B").start();
  25. new Thread(ticketSeller, "Thread C").start();
  26. new Thread(ticketSeller, "Thread D").start();
  27. }
  28. }

测试结果:

  1. Thread A sell ticket: 10
  2. Thread A sell ticket: 9
  3. Thread D sell ticket: 8
  4. Thread D sell ticket: 7
  5. Thread D sell ticket: 6
  6. Thread C sell ticket: 5
  7. Thread C sell ticket: 4
  8. Thread C sell ticket: 3
  9. Thread B sell ticket: 2
  10. Thread B sell ticket: 1

18、中断处理

  1. class TicketSeller implements Runnable {
  2. @Override
  3. public void run() {
  4. try {
  5. System.out.println("线程启动");
  6. Thread.sleep(10000);
  7. } catch (InterruptedException e) {
  8. System.out.println("线程被中断");
  9. // e.printStackTrace();
  10. }
  11. }
  12. }
  13. public class Demo01 {
  14. public static void main(String[] args) throws InterruptedException {
  15. TicketSeller ticketSeller = new TicketSeller();
  16. Thread thread = new Thread(ticketSeller, "Thread A");
  17. thread.start();
  18. System.out.println("====主线程执行===");
  19. Thread.sleep(1000);
  20. // thread.interrupt();
  21. System.out.println("线程被中断否:" + thread.isInterrupted());
  22. thread.interrupt();
  23. System.out.println("线程被中断否:" + thread.isInterrupted());
  24. System.out.println("线程被中断否2:" + thread.isInterrupted());
  25. System.out.println("主线程是否被中断:" + Thread.interrupted());
  26. System.out.println("====主线程结束===");
  27. }
  28. }

测试结果:

  1. ====主线程执行===
  2. 线程启动
  3. 线程被中断否:false
  4. 线程被中断否:true
  5. 线程被中断否2:true
  6. 主线程是否被中断:false
  7. 线程被中断
  8. ====主线程结束===

结论:

 interrupt中断该线程, isInterrupted检查该线程是否被中断, interrupted检查当前线程是否被中断。

时间: 2024-11-08 20:37:01

Java_基础知识回顾的相关文章

java基础知识回顾之java Thread类学习(八)--java多线程通信等待唤醒机制经典应用(生产者消费者)

 *java多线程--等待唤醒机制:经典的体现"生产者和消费者模型 *对于此模型,应该明确以下几点: *1.生产者仅仅在仓库未满的时候生产,仓库满了则停止生产. *2.消费者仅仅在有产品的时候才能消费,仓空则等待. *3.当消费者发现仓储没有产品可消费的时候,会唤醒等待生产者生产. *4.生产者在生产出可以消费的产品的时候,应该通知等待的消费者去消费. 下面先介绍个简单的生产者消费者例子:本例只适用于两个线程,一个线程生产,一个线程负责消费. 生产一个资源,就得消费一个资源. 代码如下: pub

java基础知识回顾之java Thread类学习(七)--java多线程通信等待唤醒机制(wait和notify,notifyAll)

1.wait和notify,notifyAll: wait和notify,notifyAll是Object类方法,因为等待和唤醒必须是同一个锁,不可以对不同锁中的线程进行唤醒,而锁可以是任意对象,所以可以被任意对象调用的方法,定义在Object基类中. wait()方法:对此对象调用wait方法导致本线程放弃对象锁,让线程处于冻结状态,进入等待线程的线程池当中.wait是指已经进入同步锁的线程,让自己暂时让出同步锁,以便使其他正在等待此锁的线程可以进入同步锁并运行,只有其它线程调用notify方

java基础知识回顾之java Thread类学习(六)--java多线程同步函数用的锁

1.验证同步函数使用的锁----普通方法使用的锁 思路:创建两个线程,同时操作同一个资源,还是用卖票的例子来验证.创建好两个线程t1,t2,t1线程走同步代码块操作tickets,t2,线程走同步函数封装的代码操作tickets,同步代码块中的锁我们可以指定.假设我们事先不知道同步函数用的是什么锁:如果在同步代码块中指定的某个锁(测试)和同步函数用的锁相同,就不会出现线程安全问题,如果锁不相同,就会发生线程安全问题. 看下面的代码:t1线程用的同步锁是obj,t2线程在操作同步函数的资源,假设不

JS基础知识回顾:引用类型(一)

在ECMAScript中引用类型是一种数据结构,用于将数据和功能组织在一起,而对象时引用类型的一个实例. 尽管ECMAScript从技术上讲是一门面向对象的语言,但它不具备传统的面向对象语言所支持的类和接口等基本结构,所以虽然说引用类型与类看起来想死,但他们并不是相同的概念. 不过引用类型有的时候也可以被称为对象定义,因为他们描述的是一类对象所具有的属性和方法. 新对象是使用new操作符后跟一个构造函数来实现的,构造函数本身就是一个函数,只不过该函数时处于创建新对象的目的而定义的. ECMASc

java基础知识回顾之javaIO类--管道流PipedOutputStream和PipedIutputStream

管道流(线程通信流):管道流的主要作用是可以进行两个线程间的通讯,分为管道输出流(PipedOutputStream).管道输入流(PipedInputStream),如果想要进行管道输出,则必须要把输出流连在输入流之上.如图所示: 1.管道输入流应该连接到管道输出流 ,输入流和输出流可以直接连接       2.使用多线程操作,结合线程进行操作.通常由某个线程从管道输入流中(PipedInputStream)对象读取.          并由其他线程将其写入到相应的端到输出流中.不能使用单线程

java基础知识回顾之java Thread类学习(五)--java多线程安全问题(锁)同步的前提

这里举个例子讲解,同步synchronized在什么地方加,以及同步的前提: * 1.必须要有两个以上的线程,才需要同步. * 2.必须是多个线程使用同一个锁. * 3.必须保证同步中只能有一个线程在运行,锁加在哪一块代码 那么我们要思考的地方有:1.知道我们写的哪些是多线程代码 2.明确共享数据 3.明确多线程运行的代码中哪些语句是操作共享数据的.. 4.要确保使用同一个锁. 下面的代码:需求:两个存户分别往银行存钱,每次村100块,分三次存完. class bank{ private int

java基础知识回顾之---java String final类普通方法

辞职了,最近一段时间在找工作,把在大二的时候学习java基础知识回顾下,拿出来跟大家分享,如果有问题,欢迎大家的指正. /*     * 按照面向对象的思想对字符串进行功能分类.     *      *      * 1,获取:     * 1.1 获取字符串中字符的个数(长度).     *         int length();     * 1.2 取字符串中的某一个字符,其中的参数index指的是字符串中序数.字符串的序数从0开始到length()-1 .     *       

python爬虫主要就是五个模块:爬虫启动入口模块,URL管理器存放已经爬虫的URL和待爬虫URL列表,html下载器,html解析器,html输出器 同时可以掌握到urllib2的使用、bs4(BeautifulSoup)页面解析器、re正则表达式、urlparse、python基础知识回顾(set集合操作)等相关内容。

本次python爬虫百步百科,里面详细分析了爬虫的步骤,对每一步代码都有详细的注释说明,可通过本案例掌握python爬虫的特点: 1.爬虫调度入口(crawler_main.py) # coding:utf-8from com.wenhy.crawler_baidu_baike import url_manager, html_downloader, html_parser, html_outputer print "爬虫百度百科调度入口" # 创建爬虫类class SpiderMai

C#学习笔记(基础知识回顾)之值类型与引用类型转换(装箱和拆箱)

一:值类型和引用类型的含义参考前一篇文章 C#学习笔记(基础知识回顾)之值类型和引用类型 1.1,C#数据类型分为在栈上分配内存的值类型和在托管堆上分配内存的引用类型.如果int只不过是栈上的一个4字节的值,该如何在它上面调用方法? 二:值类型转换为引用类型--装箱 2.1CLR对值类型进行装箱时:新分配托管堆内存,将值类型的实例字段拷贝到新分配的内存中,返回托管堆中新分配对象的地址.这个地址就是一个指向对象的引用. int i = 10; Object obj = i; 三:将引用类型转换为值