Problem p02277 (C++) — buggy submission, verdict: Time Limit Exceeded

#include <iostream>
#include <vector>

const int kLargestNumberPlusOne = 1000000000 + 1;

void swap(std::pair<char, int> &a, std::pair<char, int> &b) {
  std::pair<char, int> tmp = a;
  a = b;
  b = tmp;
}

// tail_index??????????????????????´????????????¨???????????????????°???????????´?????????´?????°??????
//?????????????????????????????¨?????????????????????????????????????????????????????????
int partition(std::vector<std::pair<char, int>> &array, int head_index,
              int tail_index) {
  int standard = array[tail_index].second;
  //?????´????°?????????°?????????????????¶????????????????????????
  //????????????????????????????¬????????´??????\\?????´???
  int tail_of_smallers = head_index;
  for (int i = head_index; i < tail_index; i++) {
    if (array[i].second <= standard) {
      swap(array[i], array[tail_of_smallers]);
      tail_of_smallers++;
    }
  }
  swap(array[tail_of_smallers], array[tail_index]);
  return tail_of_smallers;
}

void quick_sort(std::vector<std::pair<char, int>> &array, int head_index,
                int tail_index) {
  if (head_index >= tail_index)
    return;
  int boundary_index = partition(array, head_index, tail_index);
  quick_sort(array, head_index, boundary_index - 1);
  quick_sort(array, boundary_index + 1, tail_index);
}

void merge(std::vector<std::pair<char, int>> &array, int head_index,
           int boundary_index, int tail_index) {
  std::vector<std::pair<char, int>> front_buffer(boundary_index - head_index);
  for (int i = head_index; i < boundary_index; i++)
    front_buffer[i - head_index] = array[i];
  std::pair<char, int> sentinel('X', kLargestNumberPlusOne);
  front_buffer.push_back(sentinel);

  std::vector<std::pair<char, int>> back_buffer(tail_index - boundary_index);
  for (int i = boundary_index; i < tail_index; i++)
    back_buffer[i - boundary_index] = array[i];
  back_buffer.push_back(sentinel);

  auto front_buffer_iter = front_buffer.begin();
  auto back_buffer_iter = back_buffer.begin();
  for (int i = head_index; i < tail_index; i++) {
    if (front_buffer_iter->second <= back_buffer_iter->second) {
      array[i] = *front_buffer_iter;
      front_buffer_iter++;
    } else {
      array[i] = *back_buffer_iter;
      back_buffer_iter++;
    }
  }
}

void merge_sort(std::vector<std::pair<char, int>> &array, int head_index,
                int tail_index) {
  if (tail_index - head_index <= 1)
    return;
  int boundary_index = (head_index + tail_index) / 2;
  merge_sort(array, head_index, boundary_index);
  merge_sort(array, boundary_index, tail_index);
  merge(array, head_index, boundary_index, tail_index);
}

bool is_stable(const std::vector<std::pair<char, int>> &first_array,
               const std::vector<std::pair<char, int>> &second_array) {
  if (first_array.size() != second_array.size())
    return false;
  for (int i = 0; i < first_array.size(); i++) {
    if (first_array[i] != second_array[i])
      return false;
  }
  return true;
}

int main() {
  int input_size;
  std::cin >> input_size;
  std::vector<std::pair<char, int>> array(input_size);
  for (auto &item : array)
    std::cin >> item.first >> item.second;
  auto buffer = array;
  quick_sort(array, 0, input_size - 1);
  merge_sort(buffer, 0, input_size);

  // for(const auto& x : buffer)
  //     std::cout << x.first << ' ' << x.second << std::endl;

  if (is_stable(array, buffer))
    std::cout << "Stable" << std::endl;
  else
    std::cout << "Not stable" << std::endl;

  for (const auto &item : array)
    std::cout << item.first << ' ' << item.second << std::endl;

  return 0;
}

Error: TLE

Fixed submission:

#include <cstdint>
#include <cstdio>
#include <iostream>
#include <vector>

static const uint32_t kVeryLargeNumber = 0xffffffff;

class Card {
public:
  char suit;
  uint32_t value;
  Card() {}
  void copy_to(Card *);
};

void Card::copy_to(Card *clone) {
  clone->suit = this->suit;
  clone->value = this->value;
}

void swap(Card *card1, Card *card2) {
  Card tmp;
  card1->copy_to(&tmp);
  card2->copy_to(card1);
  tmp.copy_to(card2);
}

void merge(std::vector<Card> &data, int begin1, int begin2, int end2) {
  std::vector<Card> subdata1(begin2 - begin1 + 1);
  std::vector<Card> subdata2(end2 - begin2 + 1);

  for (int i = 0; i < subdata1.size(); i++) {
    data[begin1 + i].copy_to(&subdata1[i]);
  }
  subdata1[subdata1.size() - 1].suit = 'X';
  subdata1[subdata1.size() - 1].value = kVeryLargeNumber;

  for (int i = 0; i < subdata2.size(); i++) {
    data[begin2 + i].copy_to(&subdata2[i]);
  }
  subdata2[subdata2.size() - 1].suit = 'X';
  subdata2[subdata2.size() - 1].value = kVeryLargeNumber;

  int j = 0;
  int k = 0;
  for (int i = begin1; i < end2; i++) {
    if (subdata1[j].value <= subdata2[k].value) {
      subdata1[j].copy_to(&data[i]);
      j++;
    } else {
      subdata2[k].copy_to(&data[i]);
      k++;
    }
  }
}

void merge_sort(std::vector<Card> &data, int begin1, int end2) {
  if (end2 - begin1 <= 1) {
    return;
  }
  int begin2 = (begin1 + end2) / 2;
  merge_sort(data, begin1, begin2);
  merge_sort(data, begin2, end2);
  merge(data, begin1, begin2, end2);
}

int do_partition(std::vector<Card> &data, int begin, int end) {
  if (end - begin <= 1) {
    return begin;
  }
  Card pivot;
  data[end - 1].copy_to(&pivot);

  int pivot_index = 0;
  for (int i = 0; i < end - 1; i++) {
    if (data[i].value <= pivot.value) {
      swap(&data[pivot_index], &data[i]);
      pivot_index++;
    }
  }
  swap(&data[pivot_index], &data[end - 1]);
  return pivot_index;
}

void quick_sort(std::vector<Card> &data, int begin, int end) {
  if (end - begin <= 1) {
    return;
  }
  int pivot_index = do_partition(data, begin, end);
  quick_sort(data, begin, pivot_index);
  quick_sort(data, pivot_index + 1, end);
}

bool is_stable(std::vector<Card> &data1, std::vector<Card> &data2) {
  if (data1.size() != data2.size()) {
    return false;
  }
  for (int i = 0; i < data1.size(); i++) {
    if (data1[i].suit != data2[i].suit) {
      return false;
    }
  }
  return true;
}

int main() {
  int input_size;
  std::cin >> input_size;
  std::vector<Card> data(input_size);
  for (int i = 0; i < data.size(); i++) {
    std::cin >> data[i].suit >> data[i].value;
  }
  std::vector<Card> clone_data(data);

  quick_sort(data, 0, data.size());
  merge_sort(clone_data, 0, clone_data.size());

  if (is_stable(data, clone_data)) {
    puts("Stable");
  } else {
    puts("Not stable");
  }

  for (int i = 0; i < data.size(); i++) {
    printf("%c %u\\n", data[i].suit, data[i].value);
  }

  return 0;
}