دوره‌ها / JAVA / لیست‌های پویا (Java ArrayList)

لیست‌های پویا (Java ArrayList)

15 دقیقه Article

لیست‌های پویا (ArrayList): آرایه‌های بدون مرز 📈📦

بزرگترین مشکل آرایه‌های معمولی در جاوا، ثابت بودن اندازه آن‌هاست. ArrayList این مشکل را حل می‌کند؛ این کلاس یک آرایه با قابلیت تغییر اندازه خودکار است که در پکیج java.util قرار دارد.

۱. چرا از ArrayList استفاده کنیم؟

  • انعطاف‌پذیری: هر وقت بخواهید می‌توانید آیتم اضافه یا حذف کنید.
  • متدهای آماده: دارای متدهای کاربردی برای جستجو، مرتب‌سازی و دستکاری داده‌هاست.
  • دسترسی سریع: چون بر پایه آرایه است، دسترسی به یک آیتم با ایندکس (Index) بسیار سریع است.

۲. عملیات‌های اصلی 🛠️

  • add(item): اضافه کردن به انتها.
  • get(index): دریافت آیتم (شمارش از 0).
  • set(index, newValue): تغییر مقدار.
  • remove(index): حذف آیتم.
  • size(): تعداد کل آیتم‌ها.
{code_block('ArrayList<String> cars = new ArrayList<String>();\ncars.add("Volvo");\ncars.add("BMW");\nSystem.out.println(cars.get(0));')}
Generics: در داخل <> نوعِ داده را مشخص می‌کنیم. دقت کنید که فقط می‌توانید از Objects استفاده کنید (مثلاً به جای int باید از Integer استفاده کنید).

پشت صحنه ArrayList:

وقتی ظرفیت آرایه داخلی پُر شود، ArrayList یک آرایه جدید با اندازه 1.5 برابرِ قبلی می‌سازد و تمام داده‌ها را به آن منتقل می‌کند. این یعنی شما نباید نگران مدیریت حافظه باشید!

نکته پرفورمنس: اگر می‌دانید قرار است دقیقاً ۱۰۰۰ آیتم داشته باشید، در هنگام ساخت بگویید: new ArrayList<>(1000). این کار از بازسازی‌های (Resizing) متعدد و سنگینِ حافظه جلوگیری می‌کند.
<hr style="margin: 50px 0; border: 0; border-top: 1px dashed rgba(255,255,255,0.1);">

بخش تخصصی: مهندسی داده و بازدهی در جاوا ⚙️💎

در این بخش، به مفاهیمی می‌پردازیم که برای نوشتن برنامه‌های مقیاس‌پذیر و با کارایی بالا (High Performance) ضروری هستند.

۱. تحلیل پیچیدگی زمانی (Big O Notation)

انتخاب کالکشنِ اشتباه می‌تواند سرعت برنامه شما را از میلی‌ثانیه به دقیقه کاهش دهد. مثلاً پر کردن یک ArrayList با ۱ میلیون داده در صورتی که مدام از ابتدای آن حذف کنید، فاجعه‌بار است (O(n)). در حالی که LinkedList این کار را در زمان ثابت (O(1)) انجام می‌دهد. همیشه قبل از انتخاب ابزار، به نحوه دسترسی و تغییر داده‌ها فکر کنید.

۲. مدیریت حافظه (Memory Overhead)

اشیاءِ کالکشن در جاوا "ارزان" نیستند. یک HashMap یا LinkedList به ازای هر گره (Node) مقدار زیادی حافظه اضافی (Overhead) برای نگهداری ریفرنس‌های داخلی مصرف می‌کند. در سیستم‌هایی با رم محدود، گاهی اوقات استفاده از یک آرایه ساده یا کالکشن‌های تخصصیِ Primitive (مثل آنچه در کتابخانه‌های Trove یا FastUtil یافت می‌شود) گزینه‌ی بهتری است.

۳. امنیت نخ (Thread Safety) و کالکشن‌ها

اکثر کالکشن‌های پایه در جاوا (مثل ArrayList و HashMap) Thread-Safe نیستند. یعنی اگر دو نخ (Thread) همزمان سعی کنند در آن‌ها بنویسند، برنامه کراش می‌کند یا داده‌ها خراب می‌شوند. برای محیط‌های چندنخی، باید از ConcurrentHashMap یا کلاس‌های کمکی در Collections.synchronizedList استفاده کرد.

نکته طلایی: در جاوا، همیشه سعی کنید "نوعِ متغیر" را اینترفیس بگیرید و "نوعِ پیاده‌سازی" را کلاس واقعی. مثلاً: List<String> list = new ArrayList<>();. این کار تعویضِ پیاده‌سازی را در آینده بسیار راحت می‌کند.

تمرین‌های عملی

برای تثبیت یادگیری این درس تمرین‌های زیر را حل کنید

مدیریت لیست میوه‌ها Medium
سوال تمرین

یک ArrayList از نوع String به نام fruits بسازید. میوه‌های "Apple" و "Banana" را به آن اضافه کنید، سپس آیتم اول را به "Orange" تغییر دهید و لیست را چاپ کنید.

پاسخ تمرین
JAVA
import java.util.ArrayList;

public class Main {
  public static void main(String[] args) {
    ArrayList<String> fruits = new ArrayList<String>();
    fruits.add("Apple");
    fruits.add("Banana");
    fruits.set(0, "Orange");
    System.out.println(fruits);
  }
}

آماده رفتن به درس بعدی هستید؟

این درس را به پایان رساندید و می‌توانید به درس بعدی بروید.