
배열 인덱스 연산자 오버로딩을 사용하면, 배열에 사용하는  [] 연산자를 객체에도 사용할 수 있다.
[] 연산자 오버로딩은 일반적으로 많은 객체를 저장하고 관리하는 객체에 사용된다.
[] 연산자 오버로딩은 일반적으로 컨테이너 객체에 사용된다. 컨테이너 객체가 관리하는 내부 원소에 접근할 때 사용된다.
#include <iostream>
using namespace std;
class Array
{
public:
    explicit Array(const uint32_t cap = 100)
        : size(0), capacity(cap)
    {
        arr = new uint32_t[capacity];
    }
    ~Array()
    {
        if (nullptr != arr)
        {
            delete[] arr;
        }
    }
    void Add(const uint32_t num) noexcept
    {
        if (size < capacity)
        {
            arr[size++] = num;
        }
    }
    uint32_t GetSize() const noexcept
    {
        return size;
    }
    uint32_t& operator[](const uint32_t idx)
    {
        if (idx < size)
        {
            return arr[idx];
        }
        throw out_of_range("Index out of range");
    }
    uint32_t operator[](const uint32_t idx) const
    {
        if (idx < size)
        {
            return arr[idx];
        }
        throw out_of_range("Index out of range");
    }
private:
    uint32_t* arr;
    uint32_t size;
    uint32_t capacity;
};
int main()
{
    Array myArr(5);
    for (uint32_t i = 0; i < 5; i++)
    {
        myArr.Add(i * 10);
    }
    cout << "Array size: " << myArr.GetSize() << endl;
    try
    {
        for (uint32_t i = 0; i < 6; i++)
        {
            cout << "Element at index " << i << ": " << myArr[i] << endl;
        }
    }
    catch(const out_of_range& e)
    {
        cout << e.what() << endl;
    }
    cout << endl;
    myArr[0] = 555;
    for (uint32_t i = 0; i < 5; i++)
    {
        cout << "Element at index " << i << ": " << myArr[i] << endl;
    }
    return 0;
}
/* 결과
Array size: 5
Element at index 0: 0
Element at index 1: 10
Element at index 2: 20
Element at index 3: 30
Element at index 4: 40
Index out of range
Element at index 0: 555
Element at index 1: 10
Element at index 2: 20
Element at index 3: 30
Element at index 4: 40
*/
❗ [] 연산자 오버로딩은 myArr[0] = 555;와 같은 쓰기 연산도 가능해야 하므로 operator[]() 함수는 const 함수와 비 const 함수 모두를 제공해야 한다.
Array ar(10);
cout << ar[0] << endl; // ar.operator[](int) 함수를 호출!
const Array& ar2 = ar;
cout << ar2[0] << endl; // ar.operator[](int) const 함수를 호출!
operator[](int) 함수는 읽기/쓰기 연산이 모두 가능한 비 const 객체에 사용된다.operator[](int) const 함수는 읽기 연산만 가능한 const 객체에 사용된다.