Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #include <iostream>
- #include "utility"
- struct Node {
- int first;
- int second;
- int weight;
- inline bool operator<(const Node& other) const {
- return weight <= other.weight;
- }
- inline bool operator==(const Node& other) const {
- return first == other.first && second == other.second && weight == other.weight;
- }
- };
- class Mst {
- private:
- int64_t weight_min_;
- int64_t weight_pre_min_;
- int* parent_;
- Node* order_;
- Node* edges_;
- int edges_size_;
- int size_;
- public:
- explicit Mst(int size, int edges)
- : weight_min_(0), weight_pre_min_(1e9), size_(size), edges_size_(edges) {
- parent_ = new int[size_ + 1];
- edges_ = new Node[edges_size_ + 1];
- order_ = new Node[size_];
- for (int i = 1; i <= size; ++i) {
- parent_[i] = i;
- }
- }
- ~Mst() {
- delete[] parent_;
- delete[] edges_;
- delete[] order_;
- }
- void input() {
- for (int first, second, weight, i = 1; i <= edges_size_; ++i) {
- std::cin >> first >> second >> weight;
- edges_[i] = Node{first, second, weight};
- }
- quickSort(1, edges_size_);
- }
- void getMst() {
- weight_min_ = getWeight(order_);
- for (int i = 1; i <= size_; ++i) {
- parent_[i] = i;
- }
- Node* order = new Node[size_];
- for (int ind = 1; ind <= edges_size_; ++ind) {
- int tmp = edges_[ind].weight;
- edges_[ind].weight = -1;
- int64_t pre_min = getWeight(order);
- bool correct = true;
- bool another = false;
- for (int i = 1; i < size_; ++i) {
- if (!(order_[i] == order[i])) {
- another = true;
- break;
- }
- }
- for (int parent = getParent(1), j = 2; j <= size_; ++j) {
- if (getParent(j) != parent) {
- correct = false;
- break;
- }
- }
- if (correct && another) {
- weight_pre_min_ = weight_pre_min_ < pre_min ? weight_pre_min_ : pre_min;
- }
- for (int i = 1; i <= size_; ++i) {
- parent_[i] = i;
- }
- edges_[ind].weight = tmp;
- }
- delete[] order;
- }
- int64_t getWeight(Node* order) {
- int weight = 0;
- int index = 1;
- for (int i = 1; i <= edges_size_; ++i) {
- if (edges_[i].weight > 0 && getParent(edges_[i].first) != getParent(edges_[i].second)) {
- unionNodes(edges_[i].first, edges_[i].second);
- weight += edges_[i].weight;
- order[index++] = edges_[i];
- }
- }
- return weight;
- }
- void getResult() const {
- std::cout << weight_min_ << " " << weight_pre_min_ << "\n";
- }
- private:
- int getParent(int node) {
- if (parent_[node] == node) {
- return node;
- }
- int node_parent = getParent(parent_[node]);
- parent_[node] = node_parent;
- return parent_[node];
- }
- void unionNodes(int first, int second) {
- first = getParent(first);
- second = getParent(second);
- if (first != second) {
- parent_[first] = second;
- }
- }
- void swap(Node* first, Node* second) {
- Node tmp = *first;
- *first = *second;
- *second = tmp;
- }
- int partition(int low, int high) {
- int pivot = high;
- int ind = (low - 1);
- for (int j = low; j <= high - 1; ++j) {
- if (edges_[j] < edges_[pivot]) {
- ind++;
- swap(&edges_[ind], &edges_[j]);
- }
- }
- swap(&edges_[ind + 1], &edges_[high]);
- return (ind + 1);
- }
- void quickSort(int left, int right) {
- if (left < right) {
- int pi = partition(left, right);
- quickSort(left, pi - 1);
- quickSort(pi + 1, right);
- }
- }
- };
- void fastIO() {
- std::ios_base::sync_with_stdio(false);
- std::cin.tie(nullptr);
- std::cout.tie(nullptr);
- }
- int main() {
- fastIO();
- int nodes, edges;
- std::cin >> nodes >> edges;
- Mst mst(nodes, edges);
- mst.input();
- mst.getMst();
- mst.getResult();
- return 0;
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement