Chương 10: Thread và xử lý đa luồng

Câu 1: Câu nào sau đây đúng khi nói về đoạn code sau (chọn 2 đáp án)

A. compile success
B. Dòng số 6 compile eror
C. Dòng số 10 compile error
D. getFoo() và decrease() trong khi được chạy đều thực hiện khóa 1 object giống nhau
E. Trong toàn bộ chương trình sẽ chỉ có 1 object Foo được sinh ra
F. Class Foo an toàn khi dùng đa luồng
Câu 2: Compile và chạy chương trình sau kết quả là (chọn 1 đáp án)

A. Mỗi lần chạy ra 1 kết quả khác nhau
B. ab
C. ac
D. bc
E. Compile error
F. runtime error
Câu 3: Cách nào sau đây để tạo parallel Stream (stream dùng cho đa luồng). col là biến kiểu Collection và bs là biến kiểu BaseStream (chọn 1 đáp án)
A. new ParallelStream(col)
B. col.parallelStream()
C. col.parallel()
D. new ParallelStream(bs)
E. bs.parallelStream()
F. bs.parallel()
Câu 4: Compile và chạy chương trình sau kết quả là (chọn 1 đáp án)

A. 100 100
B. 100 99
C. 99 99
D. Mỗi lần chạy ra 1 kết quả
E. runtime error
F. Vòng lặp vô hạn
Câu 5: Compile và chạy chương trình sau kết quả là (chọn 1 đáp án)

A. Dòng thứ 6 compile error
B. Dòng thứ 7 compile error
C. 13
D. Mỗi lần chạy ra 1 kết quả
E. runtime error
Câu 6: Compile và chạy chương trình sau kết quả là (chọn 2 đáp án)

A. Dòng thứ 7 compile error
B. Dòng thứ 9 compile error
C. Dòng thứ 10, 11 compile error
D. 3 4
E.  4 3
F. Code trên chạy tốt với đa luồng
Câu 7: Câu nào sau đây đúng khi nói về method run() của interface Runnable và call() của interface Callable (chọn 4 đáp án)
A. Các method trên đều ko có kiểu trả về (void)
B. method call() có giá trị trả về là kiểu generics
C. method call() có đối số là kiểu generics
D. method run() có giá trị trả về là generics
E. Các method trên đều có thể dùng với lambda
F. method call() có throw checked exception
G. Cả 2 method đều throw unchecked exception
Câu 8: Code nào sau đây compile success (chọn 3 đáp án)
A. Callable o = () -> {System.out.println(“wo”); return 10;};
B. Callable o = (int c) -> c ++;
C. Callable o = () -> “hello” + “bye”;
D. Callable o = () -> {return 10};
E. Callable o = () -> 5;
F. Callable o = () -> {boolean b = true;};
G. Callable o = a -> {return “java”;};
Câu 9: Câu nào sau đây đúng khi nói về ExecutorService khi số lượng task cần chạy vượt quá số lượng thread (chọn 1 đáp án)
A. Xóa bỏ ngẫu nhiêu task
B. runtime error exception
C. task sẽ chờ đến khi thread có thể sử dụng
D. task ko thể chạy sẽ dc ghi ra log file
E. Số lượng thread có thể sử dụng nên được thiết kế nhiều hơn so với số task cần chạy
Câu 10: Chạy chương trình sau kết quả là (chọn 1 đáp án)

A. 100 100
B. Mỗi lần chạy ra 1 kết quả khác nhau
C. Dòng 13 runtime error
D. Dòng 18 runtime error
E. compile error
Câu 11: Chạy chương trình sau kết quả là (chọn 2 đáp án)

A. Dòng thứ 8 compile error
B. Dòng thứ 9 compile error
C. Dòng thứ 10 compile error
D. 10.9 2.3 end
E. Mỗi lần chạy ra 1 kết quả
F. Sau khi in ra kết quả chương trình ko kết thúc
Câu 12. Chạy chương trình sau kết quả là (chọn 2 đáp án)

A. Dòng thứ 6 compile error
B. Dòng thứ 8 compile error
C. Dòng thứ 9 compile error
D. Dòng thứ 10 compile error
E. runtime error
D. compile success
Câu 13: Nếu dòng thứ 18 có code thì compile và chạy chương trình sau kết quả là gì (chọn 2 đáp án)

A. Nếu dòng 18 trả về số int lớn hơn 0 thì sẽ in ra màn hình 10 lần số đó
B. Nếu dòng 18 trả về null thì sẽ in ra 1 lần null
C. Nếu Dòng 18 throw runtime exception thì sẽ in ra 1 lần error
D. Nếu thời gian xử lý dài thì hàm get() ở dòng 22 sẽ chờ đến khi xử lý kết thúc
E. Code hiện tại dòng 10 và 11 compile error
F. Code hiện tại dòng 22 compile errror
Câu 14: Chạy chương trình sau kết quả là (chọn 1 đáp án)

A. Compile success
B. Dòng 12 compile error
C. Dòng 18 compile error
D. Dòng 20 compile error
E. runtime error
 

  • Cách khởi tạo ParallelStream( là stream phù hợp cho đa luồng):

  • AtomicInteger sử dụng trong parallel stream bình thương nhưng biến int sử dụng trong parallel stream có khả năng bị ghi đè nên mỗi lần chạy sẽ ra 1 kết quả khác nhau
  • method groupingByConcurrent chạy an toàn với đa luồng
  • Callable interface: V call() throws Exception
  • Runable interface: void run()
  • ExecutorService khi số task vượt quá số thread thì task sẽ chờ đến khi có thể sử dụng thread
  • ExecutorService khi chạy method execute() cần phải shutdown nếu ko sẽ rơi vào trạng thái chờ
  • ExecutorService và ScheduledExecutorService có quan hệ kế thừa nhưng ExecutorService ko có phương thức scheduleWithFixedDelay(). Phương thức này cũng cần đối số đầu tiên là Runnable chứ ko phải Callable
  • Kiểu future là kiểu trả về của method submit của executorService. Nó chứa kết quả của các task chạy trong executorService có thê lấy bằng lênh get. Future.get() sẽ chờ đến khi lấy hết dc kết quả của các task vì thế sẽ block thread đang chạy.
  •  java.util.concurrent.ForkJoinPool tương tự với ExecutorService là nơi quản lý các thread để chạy các task song song chỉ khác là forkjoinpool phân chia các task thành các task nhỏ để chạy trên nhiều luồng.
    • ForkJoinTask<V>: một abstract class định nghĩa task sẽ được thực thi trong một ForkJoinPool.
    • ForkJoinPool: là một thread pool quản lý việc thực thi các ForkJoinTasks. Phải shut down sau khi kết thúc
    • RecursiveAction: là một lớp co n của ForkJoinTask, nó thực thi tác vụ mà không trả lại bất kỳ kết quả nào (action).
    • RecursiveTask<V>: là một lớp con của ForkJoinTask, nó thực thi tác vụ mà có trả lại kết quả (task).

※Tham khảo: https://gpcoder.com/3573-su-dung-fork-join-framework-voi-forkjoinpool-trong-java/

  • CopyOnWriteArrayList và ConcurrentSkipListSet đều chạy tốt khi xử lý song song
  • Deadlock là khi tất cả các thread đều bị vào trạng thái chờ mãi mãi
  • Livelock là các thread vẫn chạy nhưng ko bao giờ dừng lại
  • starvation là khi có 1 thread nào đó giữ tài nguyên quá lâu làm các thread có độ ưu tiên thấp rơi vào trạng thái chờ mãi mãi
  • CylicBarrier là class tạo rào cản. Khi đủ số lượng thread thì tất cả mới có thể chạy qua rào cản này.

  • ConcurrentHashMap ko trả về chính xác size hay isEmpty, có hỗ trợ atomic và sử dụng lock striping
  • CopyOnWriteArrayList có performance ko tốt nếu dữ liệu lớn, ko có exception ConcurrentModification
  • Future<V> có thể check isCancel và check đã chạy xong hay chưa
  • ExecuteService có  shutdown và shutdownNow nhưng chỉ có isTerminate
  • Fork/Join xây dựng theo thuật toán Work-stealing mục đích sử dụng tối đa hiệu suất của core CPU
  • Method execute của ExecuteService ko có giá trị trả về. submit  mới có giá trị trả về là kiểu future

Đáp án:

  1. A E
  2. D
  3. B F
  4. D
  5. B
  6. D F
  7. B E F G
  8. A C E
  9. C
  10. A
  11. E F
  12. C D
  13. A D
  14. E

Trả lời

Email của bạn sẽ không được hiển thị công khai. Các trường bắt buộc được đánh dấu *