Problem:
Score : 100 points

Problem Statement

Consider a string of length N consisting of 0 and 1.
The score for the string is calculated as follows:

For each i (1 \leq i \leq M), a_i is added to the score if the string contains 1 at least once between the l_i-th and r_i-th characters (inclusive).

Find the maximum possible score of a string.

Constraints

All values in input are integers.

1 \leq N \leq 2 × 10^5

1 \leq M \leq 2 × 10^5

1 \leq l_i \leq r_i \leq N

|a_i| \leq 10^9

Input

Input is given from Standard Input in the following format:

N M
l_1 r_1 a_1
l_2 r_2 a_2
:
l_M r_M a_M

Output

Print the maximum possible score of a string.

Sample Input 1

5 3
1 3 10
2 4 -10
3 5 10

Sample Output 1

20

The score for 10001 is a_1 + a_3 = 10 + 10 = 20.

Sample Input 2

3 4
1 3 100
1 1 -10
2 2 -20
3 3 -30

Sample Output 2

90

The score for 100 is a_1 + a_2 = 100 + (-10) = 90.

Sample Input 3

1 1
1 1 -10

Sample Output 3

0

The score for 0 is 0.

Sample Input 4

1 5
1 1 1000000000
1 1 1000000000
1 1 1000000000
1 1 1000000000
1 1 1000000000

Sample Output 4

5000000000

The answer may not fit into a 32-bit integer type.

Sample Input 5

6 8
5 5 3
1 1 10
1 6 -8
3 6 5
3 4 9
5 5 -2
1 3 -6
4 6 -7

Sample Output 5

10

For example, the score for 101000 is a_2 + a_3 + a_4 + a_5 + a_7 = 10 + (-8) + 5 + 9 + (-6) = 10.

Solution in C++14 (GCC 5.4.1) (judge verdict: Wrong Answer)

#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;

using ll = long long;

// 区間の情報を二分木で管理
struct LazySegmentTree{
    // 配列サイズを 2 べきにしたときのサイズ
    int sz;
    // 1-indexed で管理
    vector<ll> data;
    vector<ll> lazy;

    LazySegmentTree(int n){
        sz = 1;
        while(sz < n)   sz <<= 1;
        data.assign(sz << 1, 0);
        lazy.assign(sz << 1, 0);
    }

    void set(int idx, const int& x){
        data[idx + sz] = x;
    }

    // k : セグメント木上のインデックス
    //     (set された配列のどの区間かを表す)
    void build(){
        for(int k = sz - 1; k >= 0; --k){
            data[k] = max(data[k << 1], data[k << 1 | 1]);
        }
    }

    // 子ノードへの伝播
    void propagate(int k){
        if(lazy[k] == 0)    return;

        if(k < sz){
            lazy[k << 1] += lazy[k];
            lazy[k << 1 | 1] += lazy[k];
        }
        data[k] += lazy[k];
        lazy[k] = 0;
    }

    // [a, b) の各要素に対して x を一様加算
    ll update(int a, int b, const int x, int k = 1, int l = 0, int r = -1){
        if(r == -1) r = sz;
        
        propagate(k);

        // 更新する範囲が今見ている区間内にない
        if(b <= l || r <= a)    return data[k];

        // 更新する区間が今見ている区間を内包している
        else if(a <= l && r <= b){
            lazy[k] += (ll)x;
            propagate(k);
            return data[k];     // 子ノードの更新は遅延させる
        }

        else{
            return data[k] = max(update(a, b, x, k << 1, l, (l + r) >> 1),
                                update(a, b, x, k << 1 | 1, (l + r) >> 1, r));
        }
    }

    // [a, b) における最大値を取得
    ll query(int a, int b, int k = 1, int l = 0, int r = -1){
        if(r == -1) r = sz;
        
        propagate(k);
        
        if(b <= l || r <= a)    return 0;
        else if(a <= l && r <= b)   return data[k];
        else{
            return max(query(a, b, k << 1, l, (l + r) >> 1),
                        query(a, b, k << 1 | 1, (l + r) >> 1, r));
        }
    }

    ll operator[](const int& idx){
        return query(idx, idx + 1);
    }
};

int main(){
    int n, m;
    cin >> n >> m;
    vector<vector<pair<int, int>>> table(n + 1);
    for(int i = 0; i < m; ++i){
        int l, r, a;
        cin >> l >> r >> a;
        table[r].emplace_back(l, a);
    }
    LazySegmentTree dp(n + 1);
    for(int i = 1; i <= n; ++i){
        dp.update(i, i + 1, dp.query(0, i));
        for(auto p : table[i]){
            int l = p.first, a = p.second;
            dp.update(l, i + 1, a);
        }
    }
    cout << dp.query(0, n + 1) << endl;
}