Collections.synchronizedSet()
Tạo wrapper thread-safe cho bất kỳ Set nào. Khác với synchronizedSortedSet, nó không yêu cầu input là SortedSet và output không giữ thứ tự sắp xếp.
Ví dụ: HashSet + synchronizedSet
MainActivity.java
package com.example.syncsetdemo;
import android.os.Bundle;
import android.view.View;
import android.widget.ArrayAdapter;
import android.widget.EditText;
import android.widget.ListView;
import android.widget.Toast;
import androidx.appcompat.app.AppCompatActivity;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Set;
import java.util.HashSet;
public class MainActivity extends AppCompatActivity {
EditText name;
ArrayAdapter<String> adapter;
ArrayList<String> dataList;
Set<String> hashSet = new HashSet<>(); // Không sắp xếp
ListView listView;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
dataList = new ArrayList<>();
name = findViewById(R.id.name);
listView = findViewById(R.id.listView);
findViewById(R.id.refresh).setOnClickListener(v -> {
if (adapter != null) adapter.notifyDataSetChanged();
});
findViewById(R.id.save).setOnClickListener(v -> {
String input = name.getText().toString().trim();
if (!input.isEmpty()) {
Set<String> syncSet = Collections.synchronizedSet(hashSet);
syncSet.add(input);
dataList.clear();
dataList.addAll(syncSet); // Thứ tự không đảm bảo
adapter = new ArrayAdapter<>(this,
android.R.layout.simple_list_item_1, dataList);
listView.setAdapter(adapter);
Toast.makeText(this, "Đã thêm (thread-safe, không sắp xếp)", Toast.LENGTH_SHORT).show();
} else {
name.setError("Nhập tên");
}
});
}
}
Kết quả
Nhập: "delta", "alpha", "epsilon"
ListView hiển thị thứ tự ngẫu nhiên (tuỳ hash), ví dụ:
epsilon
alpha
delta
Quy tắc đồng bộ hóa khi lặp (QUAN TRỌNG)
Set<String> syncSet = Collections.synchronizedSet(hashSet);
// ĐÚNG - phải synchronized trên chính wrapper
synchronized (syncSet) {
for (String s : syncSet) {
// an toàn
}
}
// SAI - iterator không thread-safe
for (String s : syncSet) { ... }
So sánh: synchronizedSet vs synchronizedSortedSet
| Tiêu chí | synchronizedSet | synchronizedSortedSet |
|---|---|---|
| Input | Set bất kỳ | SortedSet (TreeSet) |
| Output giữ thứ tự | Không | Có |
| Hiệu năng | Nhẹ hơn | Chậm hơn (tree structure) |
| Phù hợp | Chỉ cần unique + thread-safe | Cần unique + sorted + thread-safe |
Thay thế hiện đại (Khuyến nghị)
// Thread-safe, không sắp xếp, hiệu năng cao Set<String> concurrentSet = ConcurrentHashMap.newKeySet(); // Hoặc Set<String> concurrentSet = Collections.newSetFromMap(new ConcurrentHashMap<>()); // Thread-safe, có sắp xếp Set<String> concurrentSorted = new ConcurrentSkipListSet<>();
ConcurrentHashMap.newKeySet() (API 24+) trả về Set view của ConcurrentHashMap - rất nhẹ và nhanh.
Tóm tắt
synchronizedSetbọc Set bất kỳ thành thread-safe.- Bắt buộc
synchronized(syncSet)khi iterate. - Android API 24+: ưu tiên
ConcurrentHashMap.newKeySet().