forked from mercyblitz/segmentfault-lessons
-
Notifications
You must be signed in to change notification settings - Fork 1
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
4cab64e
commit 94c24c6
Showing
15 changed files
with
539 additions
and
2 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
15 changes: 15 additions & 0 deletions
15
「一入 Java 深似海 」/代码/segmentfault/deep-in-java/stage-3/stage-3-lesson-4/pom.xml
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,15 @@ | ||
<?xml version="1.0" encoding="UTF-8"?> | ||
<project xmlns="http://maven.apache.org/POM/4.0.0" | ||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" | ||
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> | ||
<parent> | ||
<artifactId>stage-3</artifactId> | ||
<groupId>com.segmentfault</groupId> | ||
<version>1.0-SNAPSHOT</version> | ||
</parent> | ||
<modelVersion>4.0.0</modelVersion> | ||
|
||
<artifactId>stage-3-lesson-4</artifactId> | ||
<name>「一入 Java 深似海 」系列 :: 第三期 :: 第四节</name> | ||
<url>https://segmentfault.com/ls/1650000018320970/l/1500000018320681</url> | ||
</project> |
43 changes: 43 additions & 0 deletions
43
...main/java/com/segmentfault/deep/in/java/concurrency/ArrayBlockingQueueConcurrentDemo.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,43 @@ | ||
package com.segmentfault.deep.in.java.concurrency; | ||
|
||
import java.util.concurrent.*; | ||
import java.util.concurrent.atomic.AtomicInteger; | ||
|
||
public class ArrayBlockingQueueConcurrentDemo { | ||
|
||
public static void main(String[] args) throws InterruptedException { | ||
|
||
// 最大允许添加 2 个元素 | ||
BlockingQueue<Integer> queue = new ArrayBlockingQueue<>(2, true); | ||
// 申请 2 个大小的线程池 | ||
ExecutorService executorService = Executors.newFixedThreadPool(2); | ||
|
||
for (AtomicInteger i = new AtomicInteger(1); i.get() < 100; i.incrementAndGet()) { | ||
executorService.submit(() -> { // 写线程(1) | ||
try { | ||
queue.put(i.get()); | ||
} catch (InterruptedException e) { | ||
e.printStackTrace(); | ||
} | ||
}); | ||
|
||
executorService.submit(() -> { // 读线程(1) | ||
try { | ||
System.out.println(queue.take()); | ||
} catch (InterruptedException e) { | ||
e.printStackTrace(); | ||
} | ||
}); | ||
} | ||
|
||
// executorService.submit(() -> { // 写线程(2) | ||
// queue.put(2); | ||
// }); | ||
|
||
|
||
executorService.awaitTermination(10, TimeUnit.SECONDS); | ||
// 关闭线程池 | ||
executorService.shutdown(); | ||
|
||
} | ||
} |
46 changes: 46 additions & 0 deletions
46
...son-4/src/main/java/com/segmentfault/deep/in/java/concurrency/ArrayBlockingQueueDemo.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,46 @@ | ||
package com.segmentfault.deep.in.java.concurrency; | ||
|
||
import java.util.concurrent.ArrayBlockingQueue; | ||
import java.util.concurrent.BlockingQueue; | ||
|
||
public class ArrayBlockingQueueDemo { | ||
|
||
public static void main(String[] args) throws InterruptedException { | ||
|
||
// ArrayBlockingQueue 是有限队列 | ||
ArrayBlockingQueue<Integer> queue = new ArrayBlockingQueue(3); | ||
|
||
// Queue 添加操作中 offer 安全性高于 add 方法 | ||
// demoOfferMethod(queue); | ||
// demoAddMethod(queue); | ||
|
||
demoPutMethod(queue); | ||
// BlockingQueue 要使用 put 方法多于 offer 方法 | ||
|
||
System.out.println(queue); | ||
} | ||
|
||
private static void demoPutMethod(BlockingQueue<Integer> queue) throws InterruptedException { | ||
queue.put(1); | ||
queue.put(2); | ||
queue.put(3); | ||
// 如果超过了 capacity,? | ||
queue.put(4); | ||
} | ||
|
||
private static void demoAddMethod(BlockingQueue<Integer> queue) { | ||
queue.add(1); | ||
queue.add(2); | ||
queue.add(3); | ||
// 如果超过了 capacity,throw new IllegalStateException("Queue full") | ||
// queue.add(4); | ||
} | ||
|
||
private static void demoOfferMethod(BlockingQueue<Integer> queue) { | ||
queue.offer(1); | ||
queue.offer(2); | ||
queue.offer(3); | ||
// 如果超过了 capacity,后面的offer 会被忽略 | ||
queue.offer(4); | ||
} | ||
} |
17 changes: 17 additions & 0 deletions
17
...sson-4/src/main/java/com/segmentfault/deep/in/java/concurrency/CompletableFutureDemo.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,17 @@ | ||
package com.segmentfault.deep.in.java.concurrency; | ||
|
||
import java.util.concurrent.CompletableFuture; | ||
|
||
public class CompletableFutureDemo { | ||
|
||
public static void main(String[] args) { | ||
// CompletableFuture | ||
|
||
CompletableFuture.supplyAsync(() -> { | ||
return 1; | ||
}).thenApply(String::valueOf) | ||
// 异常的方式结束 | ||
.completeExceptionally(new RuntimeException()) | ||
; | ||
} | ||
} |
22 changes: 22 additions & 0 deletions
22
...sson-4/src/main/java/com/segmentfault/deep/in/java/concurrency/ConcurrentHashMapDemo.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,22 @@ | ||
package com.segmentfault.deep.in.java.concurrency; | ||
|
||
public class ConcurrentHashMapDemo { | ||
|
||
public static void main(String[] args) { | ||
|
||
// ConcurrentHashMap 读多写少场景 | ||
// 1.6 读(部分锁) -> 1.7 无锁(Segment) -> 1.8 无锁(红黑树——更好地解决 Hash 冲突) | ||
// ConcurrentSkipListMap 读多写多场景(如果内存足够时) | ||
|
||
// ConcurrentHashMap | ||
// table 2^n -> | ||
// n = 1 -> size = 2 | ||
// n = 2 -> size = 2^2 = 4 | ||
// n = 3 -> size = 2^3 = 8 TREEIFY_THRESHOLD | ||
// log2(8) = 3 | ||
// [0] -> [1] -> [2] | ||
// [0] -> [1] | ||
// -> [2] | ||
// n = 4 -> size = 2^4 = 16 | ||
} | ||
} |
31 changes: 31 additions & 0 deletions
31
...n-4/src/main/java/com/segmentfault/deep/in/java/concurrency/CopyOnWriteArrayListDemo.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,31 @@ | ||
package com.segmentfault.deep.in.java.concurrency; | ||
|
||
import java.util.Iterator; | ||
import java.util.concurrent.CopyOnWriteArrayList; | ||
|
||
public class CopyOnWriteArrayListDemo { | ||
|
||
public static void main(String[] args) { | ||
CopyOnWriteArrayList<Integer> list = new CopyOnWriteArrayList<>(); // Diamond 语法 | ||
|
||
// main 线程插入三条数据 | ||
// 安装 Thread ID | ||
list.add(1); | ||
// 判断当前线程 ID == main.threadId | ||
list.add(2); | ||
list.add(3); | ||
// Copy | ||
// JDK 升级两大核心性能提升 | ||
// 1. 数组 | ||
// 2. String | ||
|
||
// ConcurrentModificationException | ||
int times = 0; | ||
Iterator iterator = list.iterator(); | ||
while (iterator.hasNext() && times < 100) { | ||
iterator.next(); | ||
list.add(2); | ||
times++; | ||
} | ||
} | ||
} |
19 changes: 19 additions & 0 deletions
19
...stage-3-lesson-4/src/main/java/com/segmentfault/deep/in/java/concurrency/HashMapDemo.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,19 @@ | ||
package com.segmentfault.deep.in.java.concurrency; | ||
|
||
import java.util.HashMap; | ||
import java.util.Map; | ||
|
||
public class HashMapDemo { | ||
|
||
public static void main(String[] args) { | ||
|
||
String strValue = "Hello,World"; | ||
|
||
Integer intValue = new Integer(strValue.hashCode()); | ||
|
||
Map<Object, Object> map = new HashMap<>(); | ||
|
||
map.put(strValue, 1); | ||
map.put(intValue, 2); | ||
} | ||
} |
72 changes: 72 additions & 0 deletions
72
...age-3-lesson-4/src/main/java/com/segmentfault/deep/in/java/concurrency/Java9FlowDemo.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,72 @@ | ||
package com.segmentfault.deep.in.java.concurrency; | ||
|
||
import java.util.concurrent.*; | ||
|
||
public class Java9FlowDemo { | ||
|
||
public static void main(String[] args) throws InterruptedException { | ||
|
||
// Java 7 try-catch 语法 | ||
|
||
try (SubmissionPublisher<String> publisher = new SubmissionPublisher<>()) { | ||
|
||
// 订阅 | ||
publisher.subscribe(new Flow.Subscriber<String>() { | ||
|
||
private Flow.Subscription subscription; | ||
|
||
@Override | ||
public void onSubscribe(Flow.Subscription subscription) { | ||
this.subscription = subscription; | ||
println("已订阅"); | ||
// 订阅无限(Long.MAX_VALUE)数据 | ||
subscription.request(Long.MAX_VALUE); | ||
} | ||
|
||
@Override | ||
public void onNext(String item) { | ||
if ("exit".equalsIgnoreCase(item)) { | ||
// 取消订阅 | ||
subscription.cancel(); | ||
return; | ||
} else if ("exception".equalsIgnoreCase(item)) { | ||
throw new RuntimeException("Throw an exception..."); | ||
} | ||
println("得到数据:" + item); | ||
} | ||
|
||
@Override | ||
public void onError(Throwable throwable) { | ||
println("得到异常:" + throwable); | ||
} | ||
|
||
@Override | ||
public void onComplete() { | ||
println("操作完成"); | ||
} | ||
}); | ||
|
||
// 发布者发布数据 | ||
publisher.submit("Hello,World"); | ||
publisher.submit("2019"); | ||
|
||
// 故意抛出异常 | ||
publisher.submit("exception"); | ||
|
||
// exit 是退出命令 | ||
publisher.submit("exit"); | ||
// 当 exit 出现时,忽略后续提交 | ||
publisher.submit("ABCDEFG"); | ||
publisher.submit("HIGKLMN"); | ||
|
||
ExecutorService executor = (ExecutorService) publisher.getExecutor(); | ||
|
||
executor.awaitTermination(100, TimeUnit.MILLISECONDS); | ||
|
||
} | ||
} | ||
|
||
private static void println(Object object) { | ||
System.out.printf("[线程: %s] - %s\n", Thread.currentThread().getName(), object); | ||
} | ||
} |
43 changes: 43 additions & 0 deletions
43
...ain/java/com/segmentfault/deep/in/java/concurrency/LinkedBlockingQueueConcurrentDemo.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,43 @@ | ||
package com.segmentfault.deep.in.java.concurrency; | ||
|
||
import java.util.concurrent.*; | ||
import java.util.concurrent.atomic.AtomicInteger; | ||
|
||
public class LinkedBlockingQueueConcurrentDemo { | ||
|
||
public static void main(String[] args) throws InterruptedException { | ||
|
||
// 最大允许添加 2 个元素 | ||
BlockingQueue<Integer> queue = new LinkedBlockingQueue<>(2); | ||
// 申请 2 个大小的线程池 | ||
ExecutorService executorService = Executors.newFixedThreadPool(2); | ||
|
||
for (AtomicInteger i = new AtomicInteger(1); i.get() < 100; i.incrementAndGet()) { | ||
executorService.submit(() -> { // 写线程(1) | ||
try { | ||
queue.put(i.get()); | ||
} catch (InterruptedException e) { | ||
e.printStackTrace(); | ||
} | ||
}); | ||
|
||
executorService.submit(() -> { // 读线程(1) | ||
try { | ||
System.out.println(queue.take()); | ||
} catch (InterruptedException e) { | ||
e.printStackTrace(); | ||
} | ||
}); | ||
} | ||
|
||
// executorService.submit(() -> { // 写线程(2) | ||
// queue.put(2); | ||
// }); | ||
|
||
|
||
executorService.awaitTermination(10, TimeUnit.SECONDS); | ||
// 关闭线程池 | ||
executorService.shutdown(); | ||
|
||
} | ||
} |
51 changes: 51 additions & 0 deletions
51
...tage-3-lesson-4/src/main/java/com/segmentfault/deep/in/java/concurrency/MapEntryDemo.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,51 @@ | ||
package com.segmentfault.deep.in.java.concurrency; | ||
|
||
import java.util.HashMap; | ||
import java.util.Map; | ||
import java.util.concurrent.ConcurrentSkipListMap; | ||
|
||
public class MapEntryDemo { | ||
|
||
public static void main(String[] args) { | ||
Map<String, Integer> map = new HashMap<>(); | ||
map.put("A", 1); | ||
map.put("B", 2); | ||
map.put("C", 3); | ||
demoMap(map); | ||
|
||
System.out.println(map); | ||
|
||
//注意:Java Concurrent Map 可能未实现 Map.Entry#setValue(Object) 方法 | ||
Map<String, Integer> skipListMap = new ConcurrentSkipListMap<>(); | ||
|
||
skipListMap.put("A", 1); | ||
skipListMap.put("B", 2); | ||
skipListMap.put("C", 3); | ||
|
||
demoMap(skipListMap); | ||
|
||
System.out.println(skipListMap); | ||
} | ||
|
||
private static void demoMap(Map<String, Integer> map) { | ||
|
||
// 问题:如何让所有的成员值 +1 | ||
for (Map.Entry<String, Integer> entry : map.entrySet()) { | ||
slowApproach(entry, map); | ||
fastApproach(entry); | ||
} | ||
} | ||
|
||
private static void fastApproach(Map.Entry<String, Integer> entry) { | ||
entry.setValue(entry.getValue() + 1); | ||
} | ||
|
||
private static void slowApproach(Map.Entry<String, Integer> entry, Map<String, Integer> map) { | ||
String key = entry.getKey(); | ||
Integer value = entry.getValue(); | ||
// Key 的计算消耗时间 | ||
// +1 | ||
value += 1; | ||
map.put(key, value); | ||
} | ||
} |
Oops, something went wrong.