データ構造の基礎:スタックとキューの相互実装

Leetcode232:スタックによるキューの実装

問題概要:

2つのスタックのみを使用して、FIFO(先入先出)キューを実装します。通常のキューが備える4つの操作(pushpoppeekempty)をすべてサポートする必要があります。

アルゴリズムの考え方:

2つのスタックmainStacktempStackを活用し、新しい要素を常にスタックの底に配置することを考えます。エンキュー操作時に、まずメインストックの全要素をテンポラリストックに移し、新しい要素を追加した後、テンポラリストックの要素をメインストックに戻すことで、この要件を達成できます。

実装例:

class CustomQueue {
public:
    CustomQueue() {
        
    }
    
    void enqueue(int value) {
        // メインストックの全要素をテンポラリストックに移す
        while (!mainStack.empty()) {
            tempStack.push(mainStack.top());
            mainStack.pop();
        }
        // 新しい要素をメインストックに追加(底に配置される)
        mainStack.push(value);
        
        // テンポラリストックの要素をメインストックに戻す
        while (!tempStack.empty()) {
            mainStack.push(tempStack.top());
            tempStack.pop();
        }
    }
    
    int dequeue() {
        int element = front();
        mainStack.pop();
        return element;
    }
    
    int front() {
        return mainStack.top();
    }
    
    bool isEmpty() {
        return mainStack.empty();
    }

private:
    std::stack<int> mainStack;
    std::stack<int> tempStack;
};

Leetcode225:キューによるスタックの実装

問題概要:

2つのキューのみを使用して、LIFO(後入先出)スタックを実装します。通常スタックが備える4つの操作(pushtoppopempty)をサポートする必要があります。

アルゴリズムの考え方:

2つのキューinputQueueoutputQueueを使用します。新しい要素を追加するたびに、まず新要素をoutputQueueに入れ、inputQueueの全要素をoutputQueueに移し替えます。最後に2つのキューの役割を入れ替えることで、常に最新の要素がデキューの対象となります。

実装例:

class CustomStack {
public:
    CustomStack() {
        
    }
    
    void push(int value) {
        outputQueue.push(value);
        moveElements(inputQueue, outputQueue);
        swapQueues();
    }
    
    int pop() {
        int element = top();
        primaryQueue.pop();
        return element;
    }
    
    int top() {
        return primaryQueue.front();
    }
    
    bool isEmpty() {
        return primaryQueue.empty();
    }

private:
    std::queue<int> primaryQueue;
    std::queue<int> secondaryQueue;
    
    void moveElements(std::queue<int>& source, std::queue<int>& destination) {
        while (!source.empty()) {
            destination.push(source.front());
            source.pop();
        }
    }
    
    void swapQueues() {
        std::swap(primaryQueue, secondaryQueue);
    }
};

7月9日 22:41 投稿