std::shared_ptrで動的配列を扱う

std::shared_ptr自体は配列に対する特殊化がなく、boost::shared_arrayも標準では提供されません。
ただ、std::default_deleteは配列に対する特殊化が提供されているので、以下のように書けます。

#include <iostream>
#include <memory>
#include <string>

struct Data {
    int id;
    std::string name;

    Data() : id(0) {}
    Data(int id, const std::string& name)
        : id(id), name(name) {}

    ~Data()
    {
        std::cout << "dtor" << std::endl;
    }
};

int main()
{
    std::size_t n = 3;
    std::shared_ptr<Data> p(new Data[n], std::default_delete<Data[]>());

    p.get()[0] = { 3, "Alice" };
    p.get()[1] = { 1, "Bob" };
    p.get()[2] = { 4, "Carol" };

    for (std::size_t i = 0; i < n; ++i) {
        const Data& x = p.get()[i];
        std::cout << x.name << std::endl;
    }

    std::cout << "end main" << std::endl;
}
dtor
dtor
dtor
Alice
Bob
Carol
end main
dtor
dtor
dtor

残った問題は、shared_ptrにoperator[]がないことですが、これくらいは苦にならないかと思います。
おそらく、shared_arrayを真面目に作るとしたらコンテナの要件に合わせたりしないといけないから大変だったんじゃないかと予測します。