前提
$X_i$と$A_i$をpairで繋げれば良さそう。
$X_i$を基準にソートしなきゃなぁ(でもやり方わからん)
vector< pair < long long, long long>>のソート
#include <vector>
#include <utility>
#include <algorithm>
using namespace std;
vector<pair<long long, long long>> v;
// v[i].firstに$X_i$のデータを入れる
// v[i].secondに$A_i$のデータを入れる
sort(v.begin(), v.end()); //v[i].firstを基準に昇順ソート
石が配れるかどうか調べながら、後で使う情報を集める
この問題は、石を左から右にしか配れない。
かつ、1つのマスに1つしか石を置けない。
これより、石を置く直前を境に配れるかどうか判定を行う。
なぜ、石を置く直前を境に配れるかどうか判定を行えば良いのか。
一般的な考え方として、「変化の起こる前後に着目すると良い」というのがある。
さて、今回の「変化の起こる前後」とはどこだろうか?
今回の「変化の起こる前後」は、$X_i$で石が$A_i$個増えるというイベントである。
$X_i$で石が$A_i$個増えるまで、つまり$X_{i-1}$から$X_i-1$までは石が増えないのである。
この問題では、石は左から右にしか運べないため、$1$~$X_i-1$までに石が$X_i-1$個いなければならないことがわかる。
これをfor文で回して、この条件を満たすか調べれば良い。
石の移動量を求める
これはまず、やったことがないと思いつかないと思う。
まず、具体例を考えてみる。
初期位置と最終位置の全ての石のマスの位置の合計を求める。
マス1に2個、マス3に1個、マス4に3個あった場合、
$S_{pre} = 1 + 1 + 3 + 4 + 4 + 4$
これは最終的にマス1に1個、マス2に1個、...、マス6に1個となるため、
$S_{pos} = 1 + 2 + 3 + 4 + 5 + 6$
これより、それぞれのマスがどのくらい移動したのかは、
$S_{dif} = 0 + 1 + 0 + 0 + 1 + 2$
として表せる!
これより、石の移動した時の和は
$S_{dif} = S_{pos} - S_{pre}$ で表せば良いじゃないか!!とわかる。
思いつくかこんなもん。
感想
「変化の起こる前後に着目すると良い」という考え方は早めに身につけていきたい。
この問題だけではまだ身についたとは言えないと思うので、色々な問題をどんどん解いていきたい。
移動量は思いつかん。(n回目)
こればかりは経験なのでは...?