Giới thiệu
Mảng Java có kích thước cố định. Để "mở rộng", ta tạo mảng mới lớn hơn và copy dữ liệu qua System.arraycopy(), hoặc tốt hơn: dùng ArrayList (dynamic array).
Triển khai với System.arraycopy()
Bước 1-2: Dự án và Layout
Giống bài trước: ListView đơn giản.
Bước 3: MainActivity.java
package com.example.myapplication;
import android.os.Bundle;
import androidx.appcompat.app.AppCompatActivity;
import android.util.Log;
import android.widget.ArrayAdapter;
import android.widget.ListView;
import java.util.ArrayList;
import java.util.Arrays;
public class MainActivity extends AppCompatActivity {
ListView listView;
String[] names = {"A", "B", "C"};
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
listView = findViewById(R.id.list);
// MỞ RỘNG MẢNG: Tạo mảng mới size 5, copy mảng cũ vào
String[] extended = new String[5];
extended[3] = "D";
extended[4] = "E";
System.arraycopy(names, 0, extended, 0, names.length);
// extended = ["A", "B", "C", "D", "E"]
Log.d("ArrayExtend", "Original: " + Arrays.toString(names));
Log.d("ArrayExtend", "Extended: " + Arrays.toString(extended));
// Hiển thị trên ListView
ArrayAdapter<String> adapter = new ArrayAdapter<>(this,
android.R.layout.simple_list_item_1, extended);
listView.setAdapter(adapter);
}
}
Phân tích System.arraycopy()
System.arraycopy(src, srcPos, dest, destPos, length); // src: mảng nguồn // srcPos: vị trí bắt đầu copy trong mảng nguồn // dest: mảng đích // destPos: vị trí bắt đầu paste trong mảng đích // length: số phần tử copy
Cách tốt hơn: ArrayList (Dynamic Array)
// Khởi tạo
ArrayList<String> list = new ArrayList<>(Arrays.asList("A", "B", "C"));
// Thêm phần tử - O(1) amortized
list.add("D");
list.add("E");
list.add(1, "X"); // Chèn tại vị trí 1
// Xóa phần tử
list.remove("B"); // Xóa theo giá trị
list.remove(0); // Xóa theo index
// Truy cập
String first = list.get(0);
// Chuyển về mảng nếu cần
String[] array = list.toArray(new String[0]);
// Adapter trực tiếp hỗ trợ List
ArrayAdapter<String> adapter = new ArrayAdapter<>(this,
android.R.layout.simple_list_item_1, list);
So sánh: Array vs ArrayList
| Đặc điểm | Array [] | ArrayList |
|---|---|---|
| Kích thước | Cố định | Tự động mở rộng |
| Thêm/xóa | Phức tạp (copy mảng) | Đơn giản (add/remove) |
| Hiệu năng | Nhanh nhất (primitive) | Chậm một chút (object wrapper) |
| Generics | Hạn chế | Hỗ trợ đầy đủ |
| Memory | Ít hơn | Thêm overhead |
Khi nào dùng Array?
- Kích thước biết trước, không đổi
- Primitive type (int[], float[]) - tránh boxing
- Hiệu năng cực quan trọng (game, real-time)
- API yêu cầu array (JNI, một số library)
Khi nào dùng ArrayList?
- Kích thước thay đổi động
- Cần thêm/xóa thường xuyên
- Code sạch, dễ maintain
- Đa số trường hợp business logic
Best Practice: Mặc định dùngArrayList(hoặcListinterface). Chỉ dùng array khi có lý do cụ thể. Với ListView/RecyclerView, Adapter chấp nhận List trực tiếp.