2014-04-10 16 views
5

Tôi đã đọc TC++ PL về thành phần raw_storage_iterator. Sử dụng thành phần này, chúng tôi nhận được lợi ích hiệu suất vì nó tránh được việc chuyển nhượng (đắt tiền hơn) và sử dụng xây dựng bản sao. Nó nhìn với tôi rằng nó nên được sử dụng trong trình tự/container, nơi chúng tôi có thể có số lượng đáng kể các yếu tố và do đó số lượng các cuộc gọi chuyển nhượng có thể là tác động lớn.Thành phần raw_storage_iterator sử dụng/lợi thế trong C++

Về mặt lý thuyết, rõ ràng và nó cho tôi thấy rằng thành phần này hữu ích cho các lớp loại vùng chứa. Tuy nhiên tôi muốn hiểu nơi chúng ta nên sử dụng thành phần này (với các ví dụ thực tế) trong chi tiết bit để có được lợi ích hiệu suất của nó?

+0

inb4 "cplusplus.com hút, bạn không dám liên kết với nó"; nó nói ngay tại đó, nó được sử dụng để bạn có thể sử dụng bộ nhớ chưa được khởi tạo làm đích cho các thuật toán. Hiệu suất không được tốt hơn so với một vector dự phòng với một trình lặp lại inserter. Trừ khi bạn đang viết mã mức rất thấp, bạn không cần trình lặp này. – DanielKO

+0

@DanielKO một véc tơ dành riêng với một trình lặp lại inserter lặp lại phải thực hiện kiểm tra kích thước ở mỗi lần chèn. Trình biên dịch tìm ra rằng việc kiểm tra kích thước là không cần thiết là tương đối khó xảy ra. Bạn sẽ nhận được dự đoán chi nhánh tốt trên séc, nhưng nó vẫn sẽ nhỏ hơn văn bản 'raw_storage_iterator'. – Yakk

Trả lời

3

Tại số cppreference có mã mẫu.

Bạn có thể phân bổ khối liên kết của bộ nhớ chưa được khởi tạo thông qua một số cơ chế. Cppreferences sử dụng std::get_temporary_buffer<T> để phân bổ bộ đệm như vậy.

Sau đó, bạn có thể tạo con trỏ đến các thành phần này. Loại của con trỏ có một chút gây hiểu lầm, bởi vì nó không phải là con trỏ đến hợp lệT, mà là một khối bộ nhớ phù hợp để xây dựng một số T.

std::raw_storage_iterator có thể được điền bằng số T* đó và được yêu cầu xuất kết quả. Sau đó, bạn có thể đưa trình vòng lặp đó vào một thuật toán dự kiến ​​một trình lặp đầu ra thông thường và mọi thứ diễn ra suôn sẻ.

Nếu bạn cố gắng thực hiện điều này mà không cần raw_storage_iterator, bạn sẽ được chỉ định cho một không xây dựng T, hành vi không xác định. Thay vào đó, bạn có thể xây dựng của T trước khi xuất ra cho họ - nhưng điều đó là lãng phí, vì nó xây dựng đối tượng hai lần.

Ý tưởng cơ bản là cho phép sử dụng bộ đệm đầu ra không được khởi tạo với hiệu quả gần như hoàn hảo trong các thuật toán chuẩn. Nó không phải là một cái gì đó bạn nên sử dụng bên ngoài của một số microoptimization mã nghiêm trọng.

+0

Đây có phải là địa điểm tốt để sử dụng vị trí mới thay thế không? Điều này sẽ làm cho đối tượng được xây dựng đi vào không gian dành riêng cùng một lúc. Điều này vẫn đòi hỏi các lập trình viên để có đủ không gian, nhưng nó có vẻ như nó có thể là hiệu suất tốt hơn và an toàn khôn ngoan. – Paul

+0

@paul trình lặp này sử dụng vị trí 'mới', chỉ khi nó được gán cho nó. Trình lưu trữ dữ liệu thô cho phép bạn làm điều này như là một đầu ra cho một số thuật toán từ 'std' - một số trong đó bạn có thể không muốn cuộn tay. – Yakk

Các vấn đề liên quan