java8新特性

1.HashMap和HashSet

如果说当某一个链表的大小大于8,总容量大于64,那么就会把链表转换成红黑树结构(二叉树的一种),除了添加以外其他的效率都比链表快,所以现在的结构是数组加链表加红黑树

2.ConcurrentHashMap<K,V>

使用大量的cas算法,且取消原来的16段机制,采用了链表和红黑树

3.方法区

原来称为非堆(但是占用jvm空间),现在直接分离出来了叫做元空间,直接占用物理内存。

4.lambda表达式

函数式接口:只包含一个抽象方法的接口,称为函数式接口,使用@FunctionalInterface注解,这样做可以检查它是否是一个函数式接口。

适用前提条件:必须是一个函数式接口

定义:lambda表达式表示的是一个匿名的函数,Lambda 操作符“->”左侧:指定了Lambda 表达式需要的所有参数,右侧:指定了Lambda 体(匿名函数方法的方法体),即Lambda 表达式要执行的功能。

左侧:在无参的条件下(),有参只有一个参数的前提下可以写成(x),当然也可以去掉()写成x,多个参数的情况下都需要带()

右侧:无返回值只用一条语句可以不带{},多条语句需要带{},有返回值只有一条语句无{}情况下无需写return,多条或者有{}时需要写rreturn

原因:在加载编译的时候会自判断后编译成class字节码文件,在效率上在以前的基础上并没有提升,只是书写较为方便

public class LambdaTest1 {
	 public  static  void testA(LambdaTest1A la){
		 la.testA();
	 }
     public static void main(String[] args) {
    	 testA(()->System.out.println("hello testA"));
    	 ArrayList<Integer> list = new  ArrayList<>();
    	 list.add(321);
    	 list.add(123);
    	 list.add(342);
    	 list.add(112);
    	 //Collections.sort(list,(x,y)->x-y);从小到大
    	 Collections.sort(list,(x,y)->y-x);//从大到小
    	 System.out.println(list);
	}
}
interface   LambdaTest1A{
	   void  testA();
}
//策略设计模式
public class LambdaTest2 {
	public static List<LambdaTest2Person> test(List<LambdaTest2Person> list, Predicate<LambdaTest2Person> t) {
		ArrayList<LambdaTest2Person> list2 = new ArrayList<>();
		for (LambdaTest2Person lambdaTest2Person : list) {
			if (t.test(lambdaTest2Person)) {
				list2.add(lambdaTest2Person);
			}
		}
		return list2;
	}

	public static void main(String[] args) {
		ArrayList<LambdaTest2Person> list = new ArrayList<>();
		list.add(new LambdaTest2Person("张三", 24, 3333));
		list.add(new LambdaTest2Person("李四", 34, 8888));
		list.add(new LambdaTest2Person("王五", 15, 5555));
		list.add(new LambdaTest2Person("赵六", 34, 6666));
		//List<LambdaTest2Person> test = test(list, (x) -> x.getAge() > 30);
		//System.out.println(test);// 年龄大于35岁的
		Collections.sort(list, (x, y) -> {
			if (x.getAge() == y.getAge()) {
				return x.getSalary() - y.getSalary();
			}
			return x.getAge() - y.getAge();
		});// 先按年龄从小到大排列,年龄相同那么按工资从小到大排列
		for (LambdaTest2Person lambdaTest2Person : list) {
			System.out.println(lambdaTest2Person);
		}

	}
}

class LambdaTest2Person {
	private String name;
	private int age;
	private int salary;

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	public int getAge() {
		return age;
	}

	public void setAge(int age) {
		this.age = age;
	}

	public int getSalary() {
		return salary;
	}

	public void setSalary(int salary) {
		this.salary = salary;
	}

	public LambdaTest2Person(String name, int age, int salary) {
		this.name = name;
		this.age = age;
		this.salary = salary;
	}

	public LambdaTest2Person() {
	}

	@Override
	public String toString() {
		return "LambdaTest2Person [name=" + name + ", age=" + age + ", salary=" + salary + "]";
	}

}

 4.java8内置的函数式接口

Consumer<T>   void accept(T t)

Supplier<T>    T get()

Function<T, R>  R apply(T t)

Predicate<T>  boolean test(T t);

BiFunction<T,U,R>  R apply(T t,U u)

UnaryOperator<T>  T apply(T t)

BinaryOperator<T>  T apply(T t1,T t2)

BiConsumer<T,U>   void accept(T t,U u)

ToIntFunction<T>   参数T  返回值 int

IntFunction<R>  参数int  返回R

public class LambdaTest3 {
     public static void main(String[] args) {
    	 Consumer<String>   cm=(x)->System.out.println(x);
    	 cm.accept("consumer");
    	 Supplier<String>   sp=()->"Supplier";
    	 System.out.println(sp.get());
    	 Function<String, Integer>  fu= x-> Integer.valueOf(x);
    	 System.out.println(fu.apply("12"));
    	 Predicate<Integer> pr=(x)-> x>0;
    	 System.out.println(pr.test(5));
    	 BiFunction<Integer,Integer, Integer>  bi=(x,y)->x+y;
    	 System.out.println(bi.apply(2, 3));
	}
}

 5.方法引用与构造器引用及数组引用

方法引用

对象::实例方法    ;     类::静态方法       ;类::实例方法      ;    构造器引用    ;    类名 :: new   ;    数组引用     ;    类型[] :: new

public class LambdaTest4 {
     public static void main(String[] args) {
    	 //自我推测是建立在编译的前提下的,编译时一行一行的,例如如下
    	 String [] str={"a","b"};//成立
    	 //str={"a","b"};//编译不通过
    	 //编译时能自我推测  对象::实例方法
    	 Consumer<String>   cm=System.out::println;
    	 cm.accept("Consumer");
    	 //类::静态方法,编译时一行一行的
    	 BiFunction<Integer,Integer, Integer>  bi=Integer::compare;
    	 System.out.println(bi.apply(1, 2));
    	 //类名实例方法
    	 Function<LambdaTest2Person, Integer> fu=LambdaTest2Person::getAge;
    	 System.out.println(fu.apply(new LambdaTest2Person("张三", 23, 3333)));
    	 //类名::new   
    	 Supplier<LambdaTest2Person>  person=LambdaTest2Person::new;
    	 //无参构造
    	 LambdaTest2Person lambdaTest2Person = person.get();
    	 System.out.println(lambdaTest2Person);
    	 //类型[] :: new 
    	 Function<Integer, LambdaTest2Person[]> fun2 = LambdaTest2Person[] :: new;
    	 LambdaTest2Person[] emps = fun2.apply(20);
 		 System.out.println(emps.length);
	}
}

 6.stream流

定义:数据渠道,用于操作数据源(集合、数组等)所生成的元素序列

特点:Stream 自己不会存储元素。

Stream 不会改变源对象。相反,他们会返回一个持有结果的新Stream。

Stream 操作是延迟执行的。这意味着他们会等到需要结果的时候才执行。

也就是说需要结束以后才有结果

public class StreamTest2 {
  public static void main(String[] args) {
	//获取流的方式1
	 ArrayList<String> list = new ArrayList<>();
	 Stream<String> stream = list.stream();
		// 获取流的方式2
		String[] strs = new String[10];
		Stream<String> stream2 = Arrays.stream(strs);
		// 获取流的方式3
		Stream<String> of = Stream.of("a", "b");
		// 创建无线流
		// 迭代   static <T> UnaryOperator<T> identity() {return t -> t;},0表示起始值
		Stream<Integer> iterate = Stream.iterate(0, (x) -> x - 2);
		iterate.limit(10).forEach(System.out::println);
		System.out.println("-----------------");
		// 创建无限流
		// 生成  
		//T get();
		Stream<Double> generate = Stream.generate(() -> Math.random());
		generate.limit(10).forEach(System.out::println);
	}
}
public class StreamTest1 {
  public static void main(String[] args) {
	  ArrayList<LambdaTest2Person> list = new ArrayList<>();
		list.add(new LambdaTest2Person("张三", 24, 3333));
		list.add(new LambdaTest2Person("李四", 34, 8888));
		list.add(new LambdaTest2Person("王五", 15, 5555));
		list.add(new LambdaTest2Person("赵六", 34, 6666));
		Stream<LambdaTest2Person> stream = list.stream();
		Stream<LambdaTest2Person> stream1 = list.stream();
		Stream<LambdaTest2Person> stream2 = list.stream();
		Stream<LambdaTest2Person> stream3 = list.stream();
		// filter--  boolean test(T t);
		stream.filter((x)->x.getAge()>25).forEach(System.out::println);
		System.out.println("-----------------------");
		/*
		 * LambdaTest2Person [name=李四, age=34, salary=8888]
		 * LambdaTest2Person [name=赵六, age=34, salary=6666]
		 */
		//limit 显示的个数
		stream1.filter((x)->x.getAge()>25).limit(1).forEach(System.out::println);
		//LambdaTest2Person [name=李四, age=34, salary=8888]
		System.out.println("-----------------------");
		//skip跳过几个
		stream2.filter((x)->x.getAge()>25).skip(1).forEach(System.out::println);
		//LambdaTest2Person [name=赵六, age=34, salary=6666]
		System.out.println("-----------------------");
		//distinct()根据hashcode去重,需要重写hashcode,这里就根据相同年龄去重
		stream3.filter((x)->x.getAge()>25).distinct().forEach(System.out::println);
		//LambdaTest2Person [name=李四, age=34, salary=8888]
  }
}
class LambdaTest2Person {
	private String name;
	private int age;
	private int salary;

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	public int getAge() {
		return age;
	}

	public void setAge(int age) {
		this.age = age;
	}

	public int getSalary() {
		return salary;
	}

	public void setSalary(int salary) {
		this.salary = salary;
	}

	public LambdaTest2Person(String name, int age, int salary) {
		this.name = name;
		this.age = age;
		this.salary = salary;
	}

	public LambdaTest2Person() {
	}

	@Override
	public String toString() {
		return "LambdaTest2Person [name=" + name + ", age=" + age + ", salary=" + salary + "]";
	}
     //hashcode根据年龄去重
	@Override
	public int hashCode() {
		final int prime = 31;
		int result = 1;
		result = prime * result + age;
		return result;
	}

	@Override
	public boolean equals(Object obj) {
		if (this == obj)
			return true;
		if (obj == null)
			return false;
		if (getClass() != obj.getClass())
			return false;
		LambdaTest2Person other = (LambdaTest2Person) obj;
		if (age != other.age)
			return false;
		return true;
	}
}
public class StreamTest2 {
	public static   Stream<Character> toUpper(String str){
		ArrayList<Character> list = new  ArrayList<>();
		for (Character character : str.toUpperCase().toCharArray()) {
			list.add(character);
		}
		return  list.stream();
	}
	public static void main(String[] args) {
		System.out.println("----------");
		ArrayList<LambdaTest2Person> list = new ArrayList<>();
		list.add(new LambdaTest2Person("张三", 24, 3333));
		list.add(new LambdaTest2Person("李四", 34, 8888));
		list.add(new LambdaTest2Person("王五", 15, 5555));
		list.add(new LambdaTest2Person("赵六", 34, 6666));
		// map逐个遍历映射 获取名字 张三 李四 王五 赵六
		List<String> collect2 = list.stream().map((x) -> x.getName()).collect(Collectors.toList());
		collect2.stream().forEach(System.out::println);
		System.out.println("----------");
		//flatMap与map的区别
		//首先是map 返回的是     Stream<Stream<Character>>        
		Stream<Stream<Character>> map = Stream.of("aa","bb").map(StreamTest2::toUpper);
		//然后是flatMap Stream<Character>
		Stream<Character> flatMap = Stream.of("aa","bb").flatMap(StreamTest2::toUpper);
		// sort排序  按年龄排序  王五 张三 李四 赵六
		System.out.println("----------");
		list.stream().sorted((x, y) -> x.getAge() - y.getAge()).map((x) -> x.getName()).collect(Collectors.toList())
				.forEach(System.out::println);
		//count  统计 2 2 
		Long collect =  Stream.of(1, 2, 3, 4, 5).filter((x) -> x > 3).map((x) -> 1).collect(Collectors.counting());
		long count = Stream.of(1, 2, 3, 4, 5).filter((x) -> x > 3).map((x) -> 1).count();
		System.out.println(collect);
		System.out.println(count);
		System.out.println("----------");
		//allMatch  是否所有的都匹配  false  
		boolean allMatch = list.stream().allMatch((x)-> "张三".equals (x.getName()));
		System.out.println(allMatch);
		//anyMatch  是否一个匹配 true
		boolean anyMatch = list.stream().anyMatch((x)-> "张三".equals (x.getName()));
		System.out.println(anyMatch);
		//noneMatch  没有匹配  false
		boolean noneMatch = list.stream().noneMatch((x)-> "张三".equals (x.getName()));
		System.out.println(noneMatch);
		System.out.println("----------");
		//findFirst()  返回第一个元素  张三
		String string = list.stream().map((x)->x.getName()).findFirst().get();
		System.out.println(string);
		//findAny()  返回年龄为34的其中的任何一个人 
		LambdaTest2Person lambdaTest2Person = list.stream().filter((x)->x.getAge()==34).findAny().get();
		System.out.println(lambdaTest2Person);
		//返回最大值(也有可能是最小值) 这个是根据排序来的
		Integer integer = Stream.of(1,3,2,4,10,3,2).max((x,y)->x-y).get();
		System.out.println(integer);
		//返回最小值(也有可能是最大值) 这个是根据排序来的
		Integer integer1 = Stream.of(1,3,2,4,10,3,2).max(Integer::compare).get();
		System.out.println(integer1);
		System.out.println("----------");
		//reduce   根据所写的逐个计算,下面是求和  21  31
		Integer integer2 = Stream.of(1,2,3,4,5,6).reduce((x,y)->x+y).get();
		System.out.println(integer2);
		//10表示起始值
		Integer integer3 = Stream.of(1,2,3,4,5,6).reduce(10,(x,y)->x+y);
		System.out.println(integer3);
	}
}
public class StreamTest4 {
	public static void main(String[] args) {
		// collect(Collector c) 这个可以求和,平均值,求最大值,分组,保存到集合等
		// 求平均值
		Double collect = Stream.of(1, 3, 2, 4, 6).filter((x) -> x > 3).collect(Collectors.averagingInt((x) -> x));
		System.out.println(collect);
		System.out.println("----------");
		// 去重1 2 3 4 6
		Stream.of(1, 3, 2, 4, 6, 6, 6, 4).collect(Collectors.toSet()).forEach(System.out::println);
		;
		System.out.println("----------");
		// 先去重后分组 {大于3=[4, 6], 小于3=[1, 2, 3]}
		Map<String, List<Integer>> collect2 = Stream.of(1, 3, 2, 4, 6, 6, 6, 4).collect(Collectors.toSet()).stream()
				.collect(Collectors.groupingBy((x) -> {
					if (x > 3) {
						return "大于3";
					} else {
						return "小于3";
					}
				}));
		System.out.println(collect2);
		// 多级分组
		ArrayList<LambdaTest2Person> list = new ArrayList<>();
		list.add(new LambdaTest2Person("张三", 24, 3333));
		list.add(new LambdaTest2Person("李四", 34, 8888));
		list.add(new LambdaTest2Person("王五", 15, 5555));
		list.add(new LambdaTest2Person("赵六", 34, 6666));
		Map<String, Map<String, List<LambdaTest2Person>>> collect3 = list.stream().collect(Collectors.groupingBy((x) -> {
			if (x.getAge() > 25) {
				return "大于25";
			} else {
				return "小于25";
			}
		}, Collectors.groupingBy((x) -> {
			if (x.getSalary() > 4000) {
				return "大于4000";
			}else {
				return "小于4000";
			}
		})));
		//{大于25={大于4000=[LambdaTest2Person [name=李四, age=34, salary=8888], LambdaTest2Person [name=赵六, age=34, salary=6666]]}, 
          //小于25={大于4000=[LambdaTest2Person [name=王五, age=15, salary=5555]], 小于4000=[LambdaTest2Person [name=张三, age=24, salary=3333]]}} System.out.println(collect3); } }

7.java8的局部内部类的变更

   public static void main(String[] args) {
	   //当局部内部类使用外部的变量是会自动的添加final,在jdk1.7之前需要手动的添加
	   	  int  i=3;//在jdk1.7之前 这个前面需要添加 final ,但在jdk1.8后会自己添加
//	   	  i=5//编译错误
		  class LocalInnerTest{
			  public void test(){
				  System.out.println(i);
			  }
		  }
  }

 8.fork/join框架

 fork/join,将一个大任务,进行拆分(fork)成若干个小任务(拆到不可再拆时),再将一个个的小任务运算的结果进行join 汇总.

 工作窃取模式,充分利用多核线程;

 工作窃取:当一个线程执行完了,别的没有执行完,那么该线程会随机的去别的线程的末尾进行窃取工作任务,前提是多核cpu

//jdk1.7之前的算法   传统的算法
public class ForkJoinCalculate extends RecursiveTask<Long> {
	public static void main(String[] args) {
		long start = System.currentTimeMillis();

		ForkJoinPool pool = new ForkJoinPool();
		ForkJoinTask<Long> task = new ForkJoinCalculate(0L, 10000000000L);

		long sum = pool.invoke(task);
		System.out.println(sum);

		long end = System.currentTimeMillis();

		System.out.println("耗费的时间为: " + (end - start));
	}

	private static final long serialVersionUID = 13475679780L;

	private long start;
	private long end;

	private static final long THRESHOLD = 100000L; // 临界值

	public ForkJoinCalculate(long start, long end) {
		this.start = start;
		this.end = end;
	}

	@Override
	protected Long compute() {
		long length = end - start;

		if (length <= THRESHOLD) {
			long sum = 0;

			for (long i = start; i <= end; i++) {
				sum += i;
			}

			return sum;
		} else {
			long middle = (start + end) / 2;

			ForkJoinCalculate left = new ForkJoinCalculate(start, middle);
			left.fork(); // 拆分,并将该子任务压入线程队列

			ForkJoinCalculate right = new ForkJoinCalculate(middle + 1, end);
			right.fork();

			return left.join() + right.join();
		}

	}

}
public class NewForkJoin {
	@Test
	//顺序流,单线程的
	//parallel() 与sequential() 在并行流与顺序流之间进行切换。
    public  void  serialStream(){
    	long asLong = LongStream.rangeClosed(0, 10000000L).reduce(Long::sum).getAsLong();
    	long sum = LongStream.rangeClosed(0, 10000000L).sum();
    	System.out.println(asLong);
    	System.out.println(sum);
    }
	@Test
	//并行流  多线程的
	public  void  parallelStream1(){
		long sum = LongStream.rangeClosed(0, 10000000L).parallel().sum();
    	System.out.println(sum);
    }
}

 9.optional

目的:尽量的减少空指针异常,属于一个容器类,表示一个值存在或者不存在

public class OptionalTest {
	
    public static void main(String[] args) {    	
		//Optional<String> of = Optional.of(null);// 创建一个 Optional 实例,也会报异常,指定在这一行
		Optional<Object> empty = Optional.empty();//创建一个空的 Optional 实例
		System.out.println(empty.toString());//Optional.empty
		Optional<Object> ofNullable = Optional.ofNullable(null);//若 t 不为 null,创建 Optional 实例,否则创建空实例
		Object orElse = Optional.ofNullable(null).orElse("大帅哥");//如果调用对象包含值,返回该值,否则返回t
		System.out.println(orElse);//大帅哥
		boolean present = Optional.ofNullable(null).isPresent();// 判断是否包含值
		System.out.println(present);//false
		Object orElseGet = Optional.ofNullable(null).orElseGet(()->"大帅哥");//orElseGet(Supplier s) :如果调用对象包含值,返回该值,否则返回 s 获取的值
		System.out.println(orElseGet);//大帅哥
		//map(Function f): 如果有值对其处理,并返回处理后的Optional,否则返回 Optional.empty()
		//flatMap(Function mapper):与 map 类似,要求返回值必须是Optional
	}
}

10.接口中的新定义

类优先,接口中都实现,那么就按需加载(需要时指定),在Java 8中,在接口中添加静态方法带来了一个限制 :这些方法不能由实现它的类继承。

public class InterfaceTest extends InterfaceTestC implements InterfaceTestA,InterfaceTestB{
	public static void main(String[] args) {
            InterfaceTest interfaceTest = new InterfaceTest();
            interfaceTest.testA();//InterfaceTestC:testA优先使用类中的方法
            interfaceTest.testB();//InterfaceTestB---Override--testB,优先使用类中的方法
            
	}

	@Override
	public void testB() {
		System.out.println("InterfaceTestB---Override--testB");
	}

	@Override
	public void testC() {
		InterfaceTestA.super.testC();//多个需要重写一个使用的方法,静态方法需要用接口名调用
	}

}

interface InterfaceTestA {
	static void testA() {// 没有默认会添加public,只能是public的
		System.out.println("InterfaceTestA:testA");
	}

	default void testB() {/// 没有默认会添加public,只能是public的
		System.out.println("InterfaceTestA:testB");
	}
	default void testC() {// 没有默认会添加public,只能是public的
		System.out.println("InterfaceTestA:testC");
	}
}

interface InterfaceTestB {
	void testB();// 默认添加public abstract
	default void testC() {// 没有默认会添加public,只能是public的
		System.out.println("InterfaceTestB:testC");
	}
}

class InterfaceTestC {
	void testA() {// 没有默认会添加public,只能是public的
		System.out.println("InterfaceTestC:testA");
	}
}

11.重复注解

java8后可以重复注解@Repeatable

public class AnnotationTest {

	@MyAnnotation("a") // @Repeatable没有这个之前,不能按如下这么写
	@MyAnnotation("b")
	public void test() {

	}

	public static void main(String[] args) throws NoSuchMethodException, SecurityException {// 获取方法上的注解
		Class<? extends AnnotationTest> class1 = new AnnotationTest().getClass();
		Method method = class1.getMethod("test");
		// MyAnnotation annotation =
		// method.getAnnotation(MyAnnotation.class);//只有一次注解的时候能这么做,重复注解的则不行null
		MyAnnotation[] annotationsByType = method.getAnnotationsByType(MyAnnotation.class);// 重复注解可以这样
		for (MyAnnotation myAnnotation : annotationsByType) {
			System.out.println(myAnnotation.value());
		}
	}
}

@Repeatable(MyAnnotations.class)//添加该注解,需要一个该注解的容器,例如@interface MyAnnotations  MyAnnotation[] value();
@Target({ ElementType.METHOD, ElementType.TYPE, ElementType.FIELD })
@Retention(RetentionPolicy.RUNTIME)
@interface MyAnnotation {
	String value() default "adu";
}

@Target({ ElementType.METHOD, ElementType.TYPE, ElementType.FIELD })
@Retention(RetentionPolicy.RUNTIME)
@interface MyAnnotations {
	MyAnnotation[] value();
}

 12.新时间api

java8的时间api先线程安全的,而以前的是线程不安全的

//存在线程安全问题,java.util.concurrent.ExecutionException异常偶尔会出现;
public class OldTimeTest {
	public static void main(String[] args) throws InterruptedException, ExecutionException {
		SimpleDateFormat sdf = new SimpleDateFormat();
		sdf.applyPattern("yyyy-MM-dd");
		FutureTask<Date> futureTask = new FutureTask<>(() -> {
			return sdf.parse("2018-5-5");
		});
		ExecutorService newFixedThreadPool = Executors.newFixedThreadPool(10);
		Future<?> submit2 = newFixedThreadPool.submit(futureTask);
		System.out.println(submit2.get());// null

		Callable<Date> task = new Callable<Date>() {
			@Override
			public Date call() throws Exception {
				return sdf.parse("2018-5-5");
			}
		};
		List<Future<Date>> list = new ArrayList<>();
		for (int i = 0; i < 9; i++) {
			list.add(newFixedThreadPool.submit(task));
		}
		newFixedThreadPool.shutdown();
		for (Future<Date> future : list) {
			System.out.println(future.get());// callable的不为空
		}
	}
}

 old的解决方法

public class ThreadLocalTest {
	private static  ThreadLocal<DateFormat> threadLocal = new ThreadLocal<DateFormat>() {
		@Override
		protected DateFormat initialValue() {
			return new SimpleDateFormat("yyyy-MM-dd");//每次都产生一个新的DateFormat解决线程安全问题
		}

	};
	/**
	 * format:yyyy-MM-dd
	 * 
	 * @param str
	 * @throws ParseException
	 * @return
	 */
	public  static Date  getDate(String str) throws ParseException{
		return threadLocal.get().parse(str);
	}
}
public class OldTimeTest {
	public static void main(String[] args) throws InterruptedException, ExecutionException {
		ExecutorService newFixedThreadPool = Executors.newFixedThreadPool(10);
		Callable<Date> task = new Callable<Date>() {
			@Override
			public Date call() throws Exception {
				return ThreadLocalTest.getDate("2018-5-5");
			}
		};
		List<Future<Date>> list = new ArrayList<>();
		for (int i = 0; i < 10; i++) {
			list.add(newFixedThreadPool.submit(task));
		}
		newFixedThreadPool.shutdown();
		for (Future<Date> future : list) {
			System.out.println(future.get());
		}
	}
}

 新的时间api  使用ISO-8601标准

//DateTimeFormatter    LocalDate
public class NewLocalDateTime {
    public static void main(String[] args) throws InterruptedException, ExecutionException {
    	DateTimeFormatter df = DateTimeFormatter.ofPattern("yyyy-MM-dd");
    	ExecutorService newFixedThreadPool = Executors.newFixedThreadPool(10);
		Callable<LocalDate> task = new Callable<LocalDate>() {
			@Override
			public LocalDate call() throws Exception {
				return LocalDate.parse("2018-05-05", df);//格式需要完全一致"2018-5-5"就不行
			}
		};
		List<Future<LocalDate>> list = new ArrayList<>();
		for (int i = 0; i < 10; i++) {
			list.add(newFixedThreadPool.submit(task)) ;
		}
		for (Future<LocalDate> future : list) {
			System.out.println(future.get());
		}
		newFixedThreadPool.shutdown();
	}
}
//DateTimeFormatter    LocalDate
        public void main(String[] args) throws InterruptedException, ExecutionException {
            Instant now = Instant.now();//默认使用 UTC 时区  +8h
            System.out.println(now);//2018-08-05T07:23:22.110Z
            OffsetDateTime atOffset = now.atOffset(ZoneOffset.ofHours(8));
            long l = atOffset.toInstant().toEpochMilli();
            System.out.println(atOffset);//2018-08-05T15:23:22.110+08:00
            long epochMilli = now.toEpochMilli();
            System.out.println(epochMilli);// System.currentTimeMillis()  new Date().getTime()
            System.out.println("----------------");
            LocalDateTime localDateTime=LocalDateTime.now();//获取本地时间
            DateTimeFormatter df=DateTimeFormatter.ofPattern("yyyy年MM月dd天hh时mm分ss秒");
            String format = localDateTime.format(df);//
            System.out.println(format);
            System.out.println("----------------");
            LocalDateTime parse = LocalDateTime.parse("2006年5月6日", df);
            Instant oldTime = Instant.now();
            Thread.sleep(1000);
            Instant newTime = Instant.now();
            Duration between = Duration.between(oldTime, newTime);
            System.out.println(between.getSeconds());//1s
            //Period.between(ld2, ld1);  年月天 时间差
            //ZonedDate、ZonedTime、ZonedDateTime : 带时区的时间或日期
            //LocalDateTime ldt = LocalDateTime.now(ZoneId.of("Asia/Shanghai"));
    }

 

posted @ 2018-08-03 21:45  fatale  阅读(211)  评论(0编辑  收藏  举报