/*
 *  Copyright (c) 2019 The WebRTC project authors. All Rights Reserved.
 *
 *  Use of this source code is governed by a BSD-style license
 *  that can be found in the LICENSE file in the root of the source
 *  tree. An additional intellectual property rights grant can be found
 *  in the file PATENTS.  All contributing project authors may
 *  be found in the AUTHORS file in the root of the source tree.
 */

#ifndef TEST_PC_E2E_ANALYZER_VIDEO_MULTI_HEAD_QUEUE_H_
#define TEST_PC_E2E_ANALYZER_VIDEO_MULTI_HEAD_QUEUE_H_

#include <deque>
#include <memory>
#include <vector>

#include "absl/types/optional.h"
#include "rtc_base/checks.h"

namespace webrtc {

// A queue that allows more than one reader. Readers are independent, and all
// readers will see all elements; an inserted element stays in the queue until
// all readers have extracted it. Elements are copied and copying is assumed to
// be cheap.
template <typename T>
class MultiHeadQueue {
 public:
  // Creates queue with exactly `readers_count` readers.
  explicit MultiHeadQueue(size_t readers_count) {
    for (size_t i = 0; i < readers_count; ++i) {
      queues_.push_back(std::deque<T>());
    }
  }

  // Creates a copy of an existing head. Complexity O(MultiHeadQueue::size()).
  // `copy_index` - index of the queue that will be used as a source for
  //     copying.
  void AddHead(size_t copy_index) { queues_.push_back(queues_[copy_index]); }

  // Add value to the end of the queue. Complexity O(readers_count).
  void PushBack(T value) {
    for (auto& queue : queues_) {
      queue.push_back(value);
    }
  }

  // Extract element from specified head. Complexity O(1).
  absl::optional<T> PopFront(size_t index) {
    RTC_CHECK_LT(index, queues_.size());
    if (queues_[index].empty()) {
      return absl::nullopt;
    }
    T out = queues_[index].front();
    queues_[index].pop_front();
    return out;
  }

  // Returns element at specified head. Complexity O(1).
  absl::optional<T> Front(size_t index) const {
    RTC_CHECK_LT(index, queues_.size());
    if (queues_[index].empty()) {
      return absl::nullopt;
    }
    return queues_[index].front();
  }

  // Returns true if for specified head there are no more elements in the queue
  // or false otherwise. Complexity O(1).
  bool IsEmpty(size_t index) const {
    RTC_CHECK_LT(index, queues_.size());
    return queues_[index].empty();
  }

  // Returns size of the longest queue between all readers.
  // Complexity O(readers_count).
  size_t size() const {
    size_t size = 0;
    for (auto& queue : queues_) {
      if (queue.size() > size) {
        size = queue.size();
      }
    }
    return size;
  }

  // Returns size of the specified queue. Complexity O(1).
  size_t size(size_t index) const {
    RTC_CHECK_LT(index, queues_.size());
    return queues_[index].size();
  }

  size_t readers_count() const { return queues_.size(); }

 private:
  std::vector<std::deque<T>> queues_;
};

}  // namespace webrtc

#endif  // TEST_PC_E2E_ANALYZER_VIDEO_MULTI_HEAD_QUEUE_H_
