какой оптимальный способ реализовать push_back без накладных расходов - PullRequest
2 голосов
/ 14 июля 2020

Я пытаюсь реализовать очередь, в которой вы передаете ей объект, который нужно добавить в очередь.

struct Node {
    T data;
    Node *next, *prev;
};    
// Push data to the back of the list.
template <class T> T& CircularQueue<T>::push_back(const T&& new_data)
{
    Node* new_node = new Node();
    new_node->data = std::move(new_data);
    link_node(new_node, m_head);
    return new_node->data;
}

Проблема с моим текущим подходом в том, что слишком много накладных расходов (когда я от C меня сие беспокоит). например изображение, я добавлю объект из MyClass:

CircularQueue<MyClass> list;
list.push_back(MyClass(arg1, arg2));

Первая проблема заключается в том, что MyClass должен иметь конструктор без аргументов, который будет использоваться в Node* new_node = new Node();, поскольку создание структуры Node вызовет конструктор объекта внутри него - MyClass. Я пробовал использовать std :: vector, и этого не требовалось.

Вторая проблема - слишком много накладных расходов, list.push_back(MyClass(arg1, arg2)); создаст объект rvalue в стеке, а затем отправит его на push_back, затем он создаст новый объект (без списка аргументов) в куче, затем переместите все его элементы в новый объект, используя присвоение перемещения, есть ли более быстрое решение?

1 Ответ

2 голосов
/ 14 июля 2020

вы можете разместить свой узел обратно

template <class T> 
class CircularQueue {
    template<typename... U>
    T &emplace_back(U&&... u)
    {
       Node *new_node = new Node{{std::forward<U>(u)...}}; // <data is created here
        // link_node(new_node, m_head);
       return new_node->data;
    }
};
void foo() {
    CircularQueue<Data> x;
    // Do not create a Data, pass the parameters you need to create
    x.emplace_back(10, 20);
    // If you actually need to, you can of course copy or move an existing Data
    Data y(20, 30);
    x.emplace_back(y); // copies y
    x.emplace_back(std::move(y)); // moves y
}

https://godbolt.org/z/z68q77

...