#ifndef TLOCKFREEQUEUE_H
#define TLOCKFREEQUEUE_H

#include <QAtomicPointer>
#include <QDebug>

#ifdef COMPILE_ON_QT6
template<typename T>
class TLockFreeQueue
{
public:
    TLockFreeQueue()
        : _head(new Obj(T()))
        , _tail(_head.loadRelaxed())
    {

    }

    ~TLockFreeQueue()
    {
        T value;
        while (dequeue(value)) {}
        delete _head.loadRelaxed();  // 删除头节点
    }

    bool isEmpty()
    {
        Obj *oldHead = _head.loadRelaxed();
        Obj *oldTail = _tail.loadRelaxed();
        if (oldHead == oldTail) {
            return true; // 队列为空
        }
        return false;
    }

    void enqueue(const T &value)
    {
        Obj *node = new Obj(value);
        while (true) {
            Obj *tail = _tail.loadRelaxed();
            Obj *next = tail->next.loadRelaxed();
            if (tail == _tail.loadRelaxed()) {
                if (next == nullptr) {
                    if (tail->next.testAndSetRelaxed(nullptr, node)) {
                        _tail.storeRelaxed(node);
                        return;
                    }
                } else {
                    _tail.storeRelaxed(next);
                }
            }
        }
    }

    bool dequeue(T &value)
    {
        Obj *oldHead = _head.loadRelaxed();
        if (oldHead == _tail.loadRelaxed()) {
            return false; // 队列为空
        } else {
            Obj *oldNext = oldHead->next.loadRelaxed();
            if (_head.testAndSetRelaxed(oldHead, oldNext)) {
                value = oldNext->data;
                delete oldHead;  // 安全删除节点
                return true;
            }
        }

        return false;
    }

private:
    struct Obj {
        Obj(const T &value)
            : data(value), next(nullptr) {}
        T data;
        QAtomicPointer<Obj> next;
    };

    QAtomicPointer<Obj> _head;

    QAtomicPointer<Obj> _tail;
};
#else
template<typename T>
class TLockFreeQueue
{
public:
    TLockFreeQueue()
        : _head(new Obj(T()))
        , _tail(_head.load())
    {

    }

    ~TLockFreeQueue()
    {
        T value;
        while (dequeue(value)) {}
        delete _head.load();  // 删除头节点
    }

    bool isEmpty()
    {
        Obj *oldHead = _head.load();
        Obj *oldTail = _tail.load();
        if (oldHead == oldTail) {
            return true; // 队列为空
        }
        return false;
    }

    void enqueue(const T &value)
    {
        Obj *node = new Obj(value);
        while (true) {
            Obj *tail = _tail.load();
            Obj *next = tail->next.load();
            if (tail == _tail.load()) {
                if (next == nullptr) {
                    if (tail->next.testAndSetRelaxed(nullptr, node)) {
                        _tail.store(node);
                        return;
                    }
                } else {
                    _tail.store(next);
                }
            }
        }
    }

    bool dequeue(T &value)
    {
        Obj *oldHead = _head.load();
        if (oldHead == _tail.load()) {
            return false; // 队列为空
        } else {
            Obj *oldNext = oldHead->next.load();
            if (_head.testAndSetRelaxed(oldHead, oldNext)) {
                value = oldNext->data;
                delete oldHead;  // 安全删除节点
                return true;
            }
        }

        return false;
    }

private:
    struct Obj {
        Obj(const T &value)
            : data(value), next(nullptr) {}
        T data;
        QAtomicPointer<Obj> next;
    };

    QAtomicPointer<Obj> _head;

    QAtomicPointer<Obj> _tail;
};
#endif


#endif // TLOCKFREEQUEUE_H
