#ifdef LOCAL
//#define _GLIBCXX_DEBUG
#endif
#include <bits/stdc++.h>
using namespace std;
#define pb push_back
#define mp make_pair
#define fst first
#define snd second
#define forn(i, n) for (int i = 0; i < (int)(n); ++i)
typedef long long ll;
typedef vector<int> vi;
typedef vector<vi> vvi;
typedef vector<ll> vll;
typedef vector<char> vc;
typedef pair<int, int> pii;
typedef vector<pii> vii;
#define sz(c) (int)(c).size()
#define all(c) (c).begin(), (c).end()

struct edge
{
    int x, y, w, id;

    bool operator < (const edge &o) const
    {
        return w < o.w;
    }
};

struct diredge
{
    int to, id;
};

struct dsu
{
    int n;
    vvi dpar, rk;
    vector<vector<unordered_set<int>>> sons;
    // comp and bicomp dsu structures
    vi par;
    // bicomp tree
    vector<vector<diredge>> g;
    vector<edge> e;
    vi ans;
    // original graph

    dsu (int n_, vector<edge> ore) : n(n_), e(ore)
    {
        par.assign(n, -1);
        rk.assign(2, vi(n, 1));
        dpar.assign(2, vi(n));
        forn (i, 2) iota(all(dpar[i]), 0);
        sons.assign(2, vector<unordered_set<int>>(n));

        ans.resize(sz(e));
        g.resize(n);
        forn (i, sz(e))
        {
            g[e[i].x].pb(diredge{e[i].y, e[i].id});
            g[e[i].y].pb(diredge{e[i].x, e[i].id});
        }

        sort(all(ore));
        ans = vi(sz(ore), -1);
        for (const auto &ed : ore)
            add(ed);
    }

    void change (int layer, int x, int from, int to)
    {
        assert(dpar[layer][x] == from);
        dpar[layer][x] = to;
        sons[layer][from].erase(x);
        sons[layer][to].insert(x);
    }

    int get (int layer, int x)
    {
        if (layer == 0)
            x = get(1, x);
        if (x == -1 || dpar[layer][x] == x)
            return x;
        int to = get(layer, dpar[layer][x]);
        change(layer, x, dpar[layer][x], to);
        return to;
    }

    int bicomp (int x)
    {
        return get(1, x);
    }

    int comp (int x)
    {
        return get(0, x);
    }

    vi bfs (int layer, int x)
    {
        vi res(1, x);
        int l = 0;
        while (l < sz(res))
        {
            int cur = res[l++];
            for (int dest : sons[layer][cur])
            {
                assert(dest != cur);
                res.pb(dest);
            }
        }

        return res;
    }

    void reroot (int v)
    {
        v = bicomp(v);
        int root = v, child = -1;
        while (v != -1)
        {
            int p = bicomp(par[v]);
            par[v] = child;
            dpar[0][v] = child;
            child = v, v = p;
        }
        rk[0][root] = rk[0][child];
    }

    void merge (int x, int y, int layer, int id)
    {
        // x and y already comps / bicomps
        assert(dpar[layer][x] == x && dpar[layer][y] == y);
        if (rk[layer][x] > rk[layer][y])
            swap(x, y);

        //vi vs = bfs(layer, x);
        vi vs;
        forn (i, n) if (get(layer, i) == x)
            vs.pb(i);

        for (int v : vs)
        {
            for (diredge from : g[v]) if (get(layer, from.to) == y)
            if ((layer == 1) || (layer == 0 && from.id != id))
            {
                if (ans[from.id] == -1)
                    ans[from.id] = e[id].w - 1;
            }
        }
    }

    void add (const edge &ed)
    {
        int bx = bicomp(ed.x), by = bicomp(ed.y);
        if (bx == by)
            return;
        int cx = comp(ed.x), cy = comp(ed.y);
        if (cx != cy)
        {
            if (rk[0][cx] > rk[0][cy])
            {
                swap(bx, by);
                swap(cx, cy);
            }

            merge(cx, cy, 0, ed.id);
            reroot(bx);
            par[bx] = dpar[0][bx] = by;
            rk[0][cy] += rk[0][cx];
        }
        else
        {
            vi vs = get_path(bx, by);
            forn (i, sz(vs) - 1)
            {
                merge(vs[i], vs.back(), 1, ed.id);
                change(1, vs[i], vs[i], vs.back());
                rk[1][vs.back()] += rk[1][vs[i]];
            }
        }
    }

    vi used;
    int tms;

    vi get_path (int x, int y)
    {
        if (used.empty())
        {
            tms = 0;
            used = vi(n);
        }
        tms++;

        vi vx, vy;
        int lca = -1;

        while (true)
        {
            bool ok = false;
            forn (it, 2)
            {
                int &cur = (it == 0 ? x : y);
                cur = bicomp(cur);
                vi &vcur = (it == 0 ? vx : vy);
                if (cur != -1)
                {
                    vcur.pb(cur);
                    if (used[cur] == tms)
                    {
                        lca = cur;
                        ok = true;
                        break;
                    }

                    used[cur] = tms;
                    cur = par[cur];
                }
            }

            if (ok)
                break;
        }

        vi res;
        forn (it, 2)
        {
            vi &vcur = (it == 0 ? vx : vy);
            int pos = find(all(vcur), lca) - vcur.begin();
            assert(pos != sz(vcur));
            copy(vcur.begin(), vcur.begin() + pos + it, back_inserter(res));
        }
        assert(res.back() == lca);
        for (int v : res)
            assert(dpar[1][v] == v);
        return res;
    }
};

void solve (int n)
{
    int m;
    cin >> m;
    vector<edge> e(m);
    forn (i, m)
    {
        int x, y, w;
        cin >> x >> y >> w;
        --x, --y;
        e[i] = edge{x, y, w, i};
    }

    if (n == 10)
    {
        cerr << e[0].x << " -> " << e[0].y << endl;
        for (auto ed : e) if (ed.w <= 26)
            cerr << ed.x << ' ' << ed.y << endl;
    }

    dsu dsu(n, e);
    forn (i, m)
        cout << dsu.ans[i] << " \n"[i + 1 == m];
}

int main()
{
#ifdef LOCAL
    freopen("input.txt", "rt", stdin);
    freopen("output.txt", "w", stdout);
#endif // ONLINE_JUDGE

    ios_base::sync_with_stdio(false);
    cin.tie(nullptr);

    int n;
    while (cin >> n)
        solve(n);
}


#ifdef LOCAL
#define _GLIBCXX_DEBUG
#endif
#include <bits/stdc++.h>
using namespace std;
#define pb push_back
#define mp make_pair
#define fst first
#define snd second
#define forn(i, n) for (int i = 0; i < (int)(n); ++i)
typedef long long ll;
typedef vector<int> vi;
typedef vector<vi> vvi;
typedef vector<ll> vll;
typedef vector<char> vc;
typedef pair<int, int> pii;
typedef vector<pii> vii;
#define sz(c) (int)(c).size()
#define all(c) (c).begin(), (c).end()

struct edge
{
    int x, y, w, id;

    bool operator < (const edge &o) const
    {
        return w < o.w;
    }
};

struct diredge
{
    int to, id;
};

#define assert(...) ((void)0)

struct dsu
{
    int n;
    vvi dpar, rk;
    vector<vector<unordered_set<int>>> sons;
    // comp and bicomp dsu structures
    vi par;
    // bicomp tree
    vector<vector<diredge>> g;
    vector<edge> e;
    vi ans;
    // original graph

    dsu (int n_, vector<edge> ore) : n(n_), e(ore)
    {
        par.assign(n, -1);
        rk.assign(2, vi(n, 1));
        dpar.assign(2, vi(n));
        forn (i, 2) iota(all(dpar[i]), 0);
        sons.assign(2, vector<unordered_set<int>>(n));

        ans.resize(sz(e));
        g.resize(n);
        forn (i, sz(e))
        {
            g[e[i].x].pb(diredge{e[i].y, e[i].id});
            g[e[i].y].pb(diredge{e[i].x, e[i].id});
        }

        sort(all(ore));
        ans = vi(sz(ore), -1);
        for (const auto &ed : ore)
            add(ed);
    }

    void change (int layer, int x, int from, int to)
    {
        assert(dpar[layer][x] == from);
        dpar[layer][x] = to;
        if (from != x)
            sons[layer][from].erase(x);
        if (to != x)
            sons[layer][to].insert(x);
    }

    int get (int layer, int x)
    {
        if (layer == 0)
            x = get(1, x);
        if (x == -1 || dpar[layer][x] == x)
            return x;
        int to = get(layer, dpar[layer][x]);
        change(layer, x, dpar[layer][x], to);
        return to;
    }

    int bicomp (int x)
    {
        return get(1, x);
    }

    int comp (int x)
    {
        return get(0, x);
    }

    vi bfs (int layer, int x)
    {
        vi tmp(1, x);
        int l = 0;
        while (l < sz(tmp))
        {
            int cur = tmp[l++];
            for (int dest : sons[layer][cur])
            {
                assert(dest != cur);
                tmp.pb(dest);
            }
        }

        return tmp;
    }

    void reroot (int v)
    {
        v = bicomp(v);
        int root = v, child = -1;
        while (v != -1)
        {
            int p = bicomp(par[v]);
            par[v] = child;
            change(0, v, dpar[0][v], root);
            child = v, v = p;
        }
        rk[0][root] = rk[0][child];
    }

    void merge (int x, int y, int layer, int id)
    {
        // x and y already comps / bicomps
        assert(dpar[layer][x] == x && dpar[layer][y] == y);
        if (rk[layer][x] > rk[layer][y])
            swap(x, y);

        vi vs = bfs(layer, x);

        for (int v : vs)
        {
            for (diredge from : g[v]) if (get(layer, from.to) == y)
            if ((layer == 1) || (layer == 0 && from.id != id))
            {
                if (ans[from.id] == -1)
                    ans[from.id] = e[id].w - 1;
            }
        }
    }

    void add (const edge &ed)
    {
        int bx = bicomp(ed.x), by = bicomp(ed.y);
        if (bx == by)
            return;
        int cx = comp(ed.x), cy = comp(ed.y);
        if (cx != cy)
        {
            if (rk[0][cx] > rk[0][cy])
            {
                swap(bx, by);
                swap(cx, cy);
            }

            merge(cx, cy, 0, ed.id);
            reroot(bx);
            assert(dpar[0][bx] == bx);
            change(0, bx, bx, by);
            par[bx] = by;
            rk[0][cy] += rk[0][cx];
        }
        else
        {
            vi vs = get_path(bx, by);
            forn (i, sz(vs) - 1)
            {
                merge(vs[i], vs.back(), 1, ed.id);
                change(1, vs[i], vs[i], vs.back());
                rk[1][vs.back()] += rk[1][vs[i]];
            }
        }
    }

    vi used;
    int tms;

    vi get_path (int x, int y)
    {
        if (used.empty())
        {
            tms = 0;
            used = vi(n);
        }
        tms++;

        vi vx, vy;
        int lca = -1;

        while (true)
        {
            bool ok = false;
            forn (it, 2)
            {
                int &cur = (it == 0 ? x : y);
                cur = bicomp(cur);
                vi &vcur = (it == 0 ? vx : vy);
                if (cur != -1)
                {
                    vcur.pb(cur);
                    if (used[cur] == tms)
                    {
                        lca = cur;
                        ok = true;
                        break;
                    }

                    used[cur] = tms;
                    cur = par[cur];
                }
            }

            if (ok)
                break;
        }

        vi res;
        forn (it, 2)
        {
            vi &vcur = (it == 0 ? vx : vy);
            int pos = find(all(vcur), lca) - vcur.begin();
            assert(pos != sz(vcur));
            copy(vcur.begin(), vcur.begin() + pos + it, back_inserter(res));
        }
        assert(res.back() == lca);
        for (int v : res)
            assert(dpar[1][v] == v);
        return res;
    }
};

void solve (int n)
{
    int m;
    cin >> m;
    vector<edge> e(m);
    forn (i, m)
    {
        int x, y, w;
        cin >> x >> y >> w;
        --x, --y;
        e[i] = edge{x, y, w, i};
    }

    dsu dsu(n, e);
    forn (i, m)
        cout << dsu.ans[i] << " \n"[i + 1 == m];
}

int main()
{
#ifdef LOCAL
    freopen("input.txt", "rt", stdin);
    freopen("output.txt", "w", stdout);
#endif // ONLINE_JUDGE

    ios_base::sync_with_stdio(false);
    cin.tie(nullptr);

    int n;
    while (cin >> n)
        solve(n);
}


#ifdef LOCAL
//#define _GLIBCXX_DEBUG
#endif
#include <bits/stdc++.h>
using namespace std;
#define pb push_back
#define mp make_pair
#define fst first
#define snd second
#define forn(i, n) for (int i = 0; i < (int)(n); ++i)
typedef long long ll;
typedef vector<int> vi;
typedef vector<vi> vvi;
typedef vector<ll> vll;
typedef vector<char> vc;
typedef pair<int, int> pii;
typedef vector<pii> vii;
#define sz(c) (int)(c).size()
#define all(c) (c).begin(), (c).end()

struct edge
{
    int x, y, w, id;

    bool operator < (const edge &o) const
    {
        return w < o.w;
    }
};

struct diredge
{
    int to, id;
};

struct dsu
{
    int n;
    vector<edge> e;
    vector<vvi> comp;
    vvi in;
    vi par, ans;
    vector<unordered_set<int>> sons;
    vector<vector<diredge>> g;
    // 0 - comp, 1 - bicomp

    void add_edge (int cx, int cy)
    {
        assert(cx != cy);
        assert(par[cx] == -1);
        par[cx] = cy;
        sons[cy].insert(cx);
    }

    void del_edge (int cx, int cy)
    {
        assert(par[cx] == cy);
        par[cx] = -1;
        sons[cy].erase(cx);
    }

    void reroot (int cx)
    {
        if (par[cx] != -1)
        {
            int to = par[cx];
            reroot(to);
            del_edge(cx, to);
            add_edge(to, cx);
        }
        assert(par[cx] == -1);
    }

    dsu (int n_, vector<edge> ore) : n(n_), e(ore)
    {
        par.assign(n, -1);
        comp.assign(2, vvi(n));
        forn (i, 2) forn (j, n) comp[i][j] = vi(1, j);
        in.assign(2, vi(n));
        forn (i, 2) iota(all(in[i]), 0);
        sons.resize(n);

        g.resize(n);
        forn (i, sz(e))
        {
            g[e[i].x].pb(diredge{e[i].y, e[i].id});
            g[e[i].y].pb(diredge{e[i].x, e[i].id});
        }

        sort(all(ore));
        ans = vi(sz(ore), -1);
        for (const auto &ed : ore)
            add(ed);
    }

    int edges = 0, vers = 0;

    int merge (int x, int y, int layer, int id)
    {
        assert(e[id].id == id);
        if (layer == 0)
            assert(x == e[id].x && y == e[id].y);

        int bx = in[1][x], by = in[1][y];
        x = in[layer][x], y = in[layer][y];
        if (sz(comp[layer][x]) > sz(comp[layer][y]))
            swap(x, y);

        if (x == y)
            return y;

        for (int v : comp[layer][x])
        {
            comp[layer][y].pb(v);
            for (diredge from : g[v]) if (in[layer][from.to] == y)
            if ((layer == 1) || (layer == 0 && from.id != id))
            {
                if (ans[from.id] == -1)
                    ans[from.id] = e[id].w - 1;
            }
        }

        for (int v : comp[layer][x])
            in[layer][v] = y;

        if (layer == 1 && par[x] != -1)
            del_edge(x, par[x]);

        comp[layer][x].clear();
        comp[layer][x].shrink_to_fit();

        if (layer == 0)
        {
            reroot(bx);
            add_edge(bx, by);
        }

        return y;
    }

    void add (const edge &ed)
    {
        int x = ed.x, y = ed.y;
        if (in[1][x] == in[1][y])
        {
            assert(in[0][x] == in[0][y]);
            return;
        }

        if (in[0][x] != in[0][y])
            merge(x, y, 0, ed.id);
        else
        {
            vi vs = get_path(in[1][x], in[1][y]);
            int last = vs[0];
            int realp = par[vs.back()];
            forn (i, sz(vs) - 1)
                last = merge(comp[1][last][0], comp[1][vs[i + 1]][0], 1, ed.id);

            for (int v : vs) if (v != last)
            {
                vi memsons(all(sons[v]));
                for (int b : memsons)
                {
                    del_edge(b, v);
                    if (b != last)
                        add_edge(b, last);
                }
            }

            if (par[last] != realp)
            {
                if (par[last] != -1)
                    del_edge(last, par[last]);
                if (realp != -1)
                    add_edge(last, realp);
            }
        }
    }

    vi used;
    int tms;

    vi get_path (int x, int y)
    {
        if (used.empty())
        {
            tms = 0;
            used = vi(n);
        }
        tms++;

        vi vx, vy;
        int lca = -1;

        while (true)
        {
            bool ok = false;
            forn (it, 2)
            {
                int &cur = (it == 0 ? x : y);
                vi &vcur = (it == 0 ? vx : vy);
                if (cur != -1)
                {
                    vcur.pb(cur);
                    if (used[cur] == tms)
                    {
                        lca = cur;
                        ok = true;
                        break;
                    }

                    used[cur] = tms;
                    cur = par[cur];
                }
            }

            if (ok)
                break;
        }

        vi res;
        forn (it, 2)
        {
            vi &vcur = (it == 0 ? vx : vy);
            int pos = find(all(vcur), lca) - vcur.begin();
            assert(pos != sz(vcur));
            copy(vcur.begin(), vcur.begin() + pos + it, back_inserter(res));
        }

        return res;
    }
};

struct normal_dsu
{
    vi par;

    normal_dsu (int n)
    {
        par = vi(n);
        iota(all(par), 0);
    }

    int group (int x)
    {
        if (x == par[x])
            return x;
        return par[x] = group(par[x]);
    }

    void merge (int x, int y)
    {
        par[group(x)] = group(y);
    }
};

vi brut (int n, vector<edge> e)
{
    sort(all(e));
    vi ans(sz(e), -1);

    forn (i, sz(e))
    {
        normal_dsu dsu(n);
        forn (j, sz(e)) if (j != i)
        {
            dsu.merge(e[j].x, e[j].y);
            if (dsu.group(e[i].x) == dsu.group(e[i].y))
            {
                ans[e[i].id] = e[j].w - 1;
                break;
            }
        }
    }

    return ans;
}

void solve (int n)
{
    int m;
    cin >> m;
    vector<edge> e(m);
    forn (i, m)
    {
        int x, y, w;
        cin >> x >> y >> w;
        --x, --y;
        e[i] = edge{x, y, w, i};
    }

    dsu dsu(n, e);

//    vi bans = brut(n, e);
//    assert(dsu.ans == bans);

    forn (i, m)
        cout << dsu.ans[i] << " \n"[i + 1 == m];
}

int main()
{
#ifdef LOCAL
    freopen("input.txt", "rt", stdin);
    freopen("output.txt", "w", stdout);
#endif // ONLINE_JUDGE

    ios_base::sync_with_stdio(false);
    cin.tie(nullptr);

    int n;
    while (cin >> n)
        solve(n);
}


#ifdef LOCAL
#define _GLIBCXX_DEBUG
#endif
#include <bits/stdc++.h>
using namespace std;
#define pb push_back
#define mp make_pair
#define fst first
#define snd second
#define forn(i, n) for (int i = 0; i < (int)(n); ++i)
typedef long long ll;
typedef vector<int> vi;
typedef vector<vi> vvi;
typedef vector<ll> vll;
typedef vector<char> vc;
typedef pair<int, int> pii;
typedef vector<pii> vii;
#define sz(c) (int)(c).size()
#define all(c) (c).begin(), (c).end()

struct edge
{
    int x, y, w, id;

    bool operator < (const edge &o) const
    {
        return w < o.w;
    }
};

struct diredge
{
    int to, id;
};

struct dsu
{
    int n;
    vvi dpar, rk;
    vector<vector<unordered_set<int>>> sons;
    // comp and bicomp dsu structures
    vi par;
    // bicomp tree
    vector<vector<diredge>> g;
    vector<edge> e;
    vi ans;
    // original graph

    dsu (int n_, vector<edge> ore) : n(n_), e(ore)
    {
        par.assign(n, -1);
        rk.assign(2, vi(n, 1));
        dpar.assign(2, vi(n));
        forn (i, 2) iota(all(dpar[i]), 0);
        sons.assign(2, vector<unordered_set<int>>(n));

        ans.resize(sz(e));
        g.resize(n);
        forn (i, sz(e))
        {
            g[e[i].x].pb(diredge{e[i].y, e[i].id});
            g[e[i].y].pb(diredge{e[i].x, e[i].id});
        }

        sort(all(ore));
        ans = vi(sz(ore), -1);
        for (const auto &ed : ore)
            add(ed);
    }

    void change (int layer, int x, int from, int to)
    {
        assert(dpar[layer][x] == from);
        dpar[layer][x] = to;
        sons[layer][from].erase(x);
        if (to != x)
            sons[layer][to].insert(x);
    }

    int get (int layer, int x)
    {
        if (layer == 0)
            x = get(1, x);
        if (x == -1 || dpar[layer][x] == x)
            return x;
        int to = get(layer, dpar[layer][x]);
        change(layer, x, dpar[layer][x], to);
        return to;
    }

    int bicomp (int x)
    {
        return get(1, x);
    }

    int comp (int x)
    {
        return get(0, x);
    }

    vi bfs (int layer, int x)
    {
        vi tmp(1, x);
        int l = 0;
        while (l < sz(tmp))
        {
            int cur = tmp[l++];
            for (int dest : sons[layer][cur])
            {
                assert(dest != cur);
                tmp.pb(dest);
            }
        }

        vi res = tmp;
//        if (!layer)
//        {
//            vi ntmp;
//            for (int v : tmp)
//                ntmp.pb(bicomp(v));
//            sort(all(ntmp));
//            ntmp.resize(unique(all(ntmp)) - ntmp.begin());
//            res.clear();
//            for (int v : ntmp)
//            {
//                vi cur = bfs(1, v);
//                res.insert(res.end(), all(cur));
//            }
//        }

        return res;
    }

    void reroot (int v)
    {
        v = bicomp(v);
        int root = v, child = -1;
        while (v != -1)
        {
            int p = bicomp(par[v]);
            par[v] = child;
            change(0, v, dpar[0][v], root);
            child = v, v = p;
        }
        rk[0][root] = rk[0][child];
    }

    void merge (int x, int y, int layer, int id)
    {
        // x and y already comps / bicomps
        assert(dpar[layer][x] == x && dpar[layer][y] == y);
        if (rk[layer][x] > rk[layer][y])
            swap(x, y);

        vi vs = bfs(layer, x);

        for (int v : vs)
        {
            for (diredge from : g[v]) if (get(layer, from.to) == y)
            if ((layer == 1) || (layer == 0 && from.id != id))
            {
                if (ans[from.id] == -1)
                    ans[from.id] = e[id].w - 1;
            }
        }
    }

    void add (const edge &ed)
    {
        int bx = bicomp(ed.x), by = bicomp(ed.y);
        if (bx == by)
            return;
        int cx = comp(ed.x), cy = comp(ed.y);
        if (cx != cy)
        {
            if (rk[0][cx] > rk[0][cy])
            {
                swap(bx, by);
                swap(cx, cy);
            }

            merge(cx, cy, 0, ed.id);
            reroot(bx);
            assert(dpar[0][bx] == bx);
            change(0, bx, bx, by);
            par[bx] = by;
            rk[0][cy] += rk[0][cx];
        }
        else
        {
            vi vs = get_path(bx, by);
            forn (i, sz(vs) - 1)
            {
                merge(vs[i], vs.back(), 1, ed.id);
                change(1, vs[i], vs[i], vs.back());
                rk[1][vs.back()] += rk[1][vs[i]];
            }
        }
    }

    vi used;
    int tms;

    vi get_path (int x, int y)
    {
        if (used.empty())
        {
            tms = 0;
            used = vi(n);
        }
        tms++;

        vi vx, vy;
        int lca = -1;

        while (true)
        {
            bool ok = false;
            forn (it, 2)
            {
                int &cur = (it == 0 ? x : y);
                cur = bicomp(cur);
                vi &vcur = (it == 0 ? vx : vy);
                if (cur != -1)
                {
                    vcur.pb(cur);
                    if (used[cur] == tms)
                    {
                        lca = cur;
                        ok = true;
                        break;
                    }

                    used[cur] = tms;
                    cur = par[cur];
                }
            }

            if (ok)
                break;
        }

        vi res;
        forn (it, 2)
        {
            vi &vcur = (it == 0 ? vx : vy);
            int pos = find(all(vcur), lca) - vcur.begin();
            assert(pos != sz(vcur));
            copy(vcur.begin(), vcur.begin() + pos + it, back_inserter(res));
        }
        assert(res.back() == lca);
        for (int v : res)
            assert(dpar[1][v] == v);
        return res;
    }
};

void solve (int n)
{
    int m;
    cin >> m;
    vector<edge> e(m);
    forn (i, m)
    {
        int x, y, w;
        cin >> x >> y >> w;
        --x, --y;
        e[i] = edge{x, y, w, i};
    }

    if (n == 10)
    {
        cerr << e[0].x << " -> " << e[0].y << endl;
        for (auto ed : e) if (ed.w <= 26)
            cerr << ed.x << ' ' << ed.y << endl;
    }

    dsu dsu(n, e);
    forn (i, m)
        cout << dsu.ans[i] << " \n"[i + 1 == m];
}

int main()
{
#ifdef LOCAL
    freopen("input.txt", "rt", stdin);
    freopen("output.txt", "w", stdout);
#endif // ONLINE_JUDGE

    ios_base::sync_with_stdio(false);
    cin.tie(nullptr);

    int n;
    while (cin >> n)
        solve(n);
}


#ifdef LOCAL
#define _GLIBCXX_DEBUG
#endif
#include <bits/stdc++.h>
using namespace std;
#define pb push_back
#define mp make_pair
#define fst first
#define snd second
#define forn(i, n) for (int i = 0; i < (int)(n); ++i)
typedef long long ll;
typedef vector<int> vi;
typedef vector<vi> vvi;
typedef vector<ll> vll;
typedef vector<char> vc;
typedef pair<int, int> pii;
typedef vector<pii> vii;
#define sz(c) (int)(c).size()
#define all(c) (c).begin(), (c).end()

struct edge
{
    int x, y, w, id;

    bool operator < (const edge &o) const
    {
        return w < o.w;
    }
};

struct diredge
{
    int to, id;
};

struct dsu
{
    int n;
    vvi dpar, rk;
    vector<vector<unordered_set<int>>> sons;
    // comp and bicomp dsu structures
    vi par;
    // bicomp tree
    vector<vector<diredge>> g;
    vector<edge> e;
    vi ans;
    // original graph

    dsu (int n_, vector<edge> ore) : n(n_), e(ore)
    {
        par.assign(n, -1);
        rk.assign(2, vi(n, 1));
        dpar.assign(2, vi(n));
        forn (i, 2) iota(all(dpar[i]), 0);
        sons.assign(2, vector<unordered_set<int>>(n));

        ans.resize(sz(e));
        g.resize(n);
        forn (i, sz(e))
        {
            g[e[i].x].pb(diredge{e[i].y, e[i].id});
            g[e[i].y].pb(diredge{e[i].x, e[i].id});
        }

        sort(all(ore));
        ans = vi(sz(ore), -1);
        for (const auto &ed : ore)
            add(ed);
    }

    void change (int layer, int x, int from, int to)
    {
        assert(dpar[layer][x] == from);
        dpar[layer][x] = to;
        sons[layer][from].erase(x);
        if (to != x)
            sons[layer][to].insert(x);
    }

    int get (int layer, int x)
    {
        if (layer == 0)
            x = get(1, x);
        if (x == -1 || dpar[layer][x] == x)
            return x;
        int to = get(layer, dpar[layer][x]);
        change(layer, x, dpar[layer][x], to);
        return to;
    }

    int bicomp (int x)
    {
        return get(1, x);
    }

    int comp (int x)
    {
        return get(0, x);
    }

    vi bfs (int layer, int x)
    {
        vi tmp(1, x);
        int l = 0;
        while (l < sz(tmp))
        {
            int cur = tmp[l++];
            for (int dest : sons[layer][cur])
            {
                assert(dest != cur);
                tmp.pb(dest);
            }
        }

        return tmp;
    }

    void reroot (int v)
    {
        v = bicomp(v);
        int root = v, child = -1;
        while (v != -1)
        {
            int p = bicomp(par[v]);
            par[v] = child;
            change(0, v, dpar[0][v], root);
            child = v, v = p;
        }
        rk[0][root] = rk[0][child];
    }

    void merge (int x, int y, int layer, int id)
    {
        // x and y already comps / bicomps
        assert(dpar[layer][x] == x && dpar[layer][y] == y);
        if (rk[layer][x] > rk[layer][y])
            swap(x, y);

        vi vs = bfs(layer, x);

        for (int v : vs)
        {
            for (diredge from : g[v]) if (get(layer, from.to) == y)
            if ((layer == 1) || (layer == 0 && from.id != id))
            {
                if (ans[from.id] == -1)
                    ans[from.id] = e[id].w - 1;
            }
        }
    }

    void add (const edge &ed)
    {
        int bx = bicomp(ed.x), by = bicomp(ed.y);
        if (bx == by)
            return;
        int cx = comp(ed.x), cy = comp(ed.y);
        if (cx != cy)
        {
            if (rk[0][cx] > rk[0][cy])
            {
                swap(bx, by);
                swap(cx, cy);
            }

            merge(cx, cy, 0, ed.id);
            reroot(bx);
            assert(dpar[0][bx] == bx);
            change(0, bx, bx, by);
            par[bx] = by;
            rk[0][cy] += rk[0][cx];
        }
        else
        {
            vi vs = get_path(bx, by);
            forn (i, sz(vs) - 1)
            {
                merge(vs[i], vs.back(), 1, ed.id);
                change(1, vs[i], vs[i], vs.back());
                rk[1][vs.back()] += rk[1][vs[i]];
            }
        }
    }

    vi used;
    int tms;

    vi get_path (int x, int y)
    {
        if (used.empty())
        {
            tms = 0;
            used = vi(n);
        }
        tms++;

        vi vx, vy;
        int lca = -1;

        while (true)
        {
            bool ok = false;
            forn (it, 2)
            {
                int &cur = (it == 0 ? x : y);
                cur = bicomp(cur);
                vi &vcur = (it == 0 ? vx : vy);
                if (cur != -1)
                {
                    vcur.pb(cur);
                    if (used[cur] == tms)
                    {
                        lca = cur;
                        ok = true;
                        break;
                    }

                    used[cur] = tms;
                    cur = par[cur];
                }
            }

            if (ok)
                break;
        }

        vi res;
        forn (it, 2)
        {
            vi &vcur = (it == 0 ? vx : vy);
            int pos = find(all(vcur), lca) - vcur.begin();
            assert(pos != sz(vcur));
            copy(vcur.begin(), vcur.begin() + pos + it, back_inserter(res));
        }
        assert(res.back() == lca);
        for (int v : res)
            assert(dpar[1][v] == v);
        return res;
    }
};

void solve (int n)
{
    int m;
    cin >> m;
    vector<edge> e(m);
    forn (i, m)
    {
        int x, y, w;
        cin >> x >> y >> w;
        --x, --y;
        e[i] = edge{x, y, w, i};
    }

    if (n == 10)
    {
        cerr << e[0].x << " -> " << e[0].y << endl;
        for (auto ed : e) if (ed.w <= 26)
            cerr << ed.x << ' ' << ed.y << endl;
    }

    dsu dsu(n, e);
    forn (i, m)
        cout << dsu.ans[i] << " \n"[i + 1 == m];
}

int main()
{
#ifdef LOCAL
    freopen("input.txt", "rt", stdin);
    freopen("output.txt", "w", stdout);
#endif // ONLINE_JUDGE

    ios_base::sync_with_stdio(false);
    cin.tie(nullptr);

    int n;
    while (cin >> n)
        solve(n);
}


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

const int maxn = 200001;
const int logn = 21;
const int inf = 1e9 + 1;

struct edge {
	int u, v, w, id;
	edge() {}
	edge(int v, int w, int id) :v(v), w(w), id(id) {}
	edge(int u, int v, int w, int id) :u(u), v(v), w(w), id(id) {}
	bool operator <(const edge &e) const { return w < e.w; }
};

edge e[maxn];
vector<edge> adj[maxn];
int anc[maxn][logn];
int maxw[maxn][logn];
int lazy[maxn][logn];
int to_prt[maxn];
int w[maxn];
int dep[maxn];
int ans[maxn];
bool is_on[maxn];
int n, m;

void kruskal();
void dfs(int u);
void change(int u, int p, int w);
int cal_lca(int u, int v);
int cal_maxw(int u, int p);

int main() {
	scanf("%d%d", &n, &m);
	for (int i = 1; i <= m; i++) {
		int u, v, w;
		scanf("%d%d%d", &u, &v, &w);
		e[i] = edge(u, v, w, i);
	}
	kruskal();
	dep[1] = 1;
	dfs(1);
	for (int i = 1; i <= m; i++) {
		if (is_on[e[i].id]) continue;
		int lca = cal_lca(e[i].u, e[i].v);
		change(e[i].u, lca, e[i].w);
		change(e[i].v, lca, e[i].w);
		int cur = max(cal_maxw(e[i].u, lca), cal_maxw(e[i].v, lca));
		ans[e[i].id] = cur - 1;
	}
	for (int j = logn - 1; j >= 1; j--) {
		for (int i = 1; i <= n; i++) {
			if (dep[i] - (1 << j) <= 0) continue;
			lazy[i][j - 1] = min(lazy[i][j - 1], lazy[i][j]);
			lazy[anc[i][j - 1]][j - 1] = min(lazy[anc[i][j - 1]][j - 1], lazy[i][j]);
		}
	}
	for (int i = 2; i <= n; i++) {
		w[i] = lazy[i][0];
		if (w[i] < inf) ans[to_prt[i]] = w[i] - 1;
		else ans[to_prt[i]] = -1;
	}
	for (int i = 1; i <= m; i++) {
		printf("%d ", ans[i]);
	}
	return 0;
}

int p[maxn];

int find_root(int a) {
	if (p[a] == a) return a;
	return p[a] = find_root(p[a]);
}

void merge(int a, int b) {
	p[find_root(a)] = find_root(b);
}

void kruskal() {
	for (int i = 1; i <= n; i++) {
		p[i] = i;
	}
	sort(e + 1, e + 1 + m);
	for (int i = 1; i <= m; i++) {
		if (find_root(e[i].u) == find_root(e[i].v)) continue;
		merge(e[i].u, e[i].v);
		is_on[e[i].id] = 1;
		adj[e[i].u].push_back(edge(e[i].v, e[i].w, e[i].id));
		adj[e[i].v].push_back(edge(e[i].u, e[i].w, e[i].id));
	}
}

void dfs(int u) {
	for (int i = 1; i < logn; i++) {
		if (dep[u] - (1 << i) <= 0) continue;
		anc[u][i] = anc[anc[u][i - 1]][i - 1];
		maxw[u][i] = max(maxw[u][i - 1], maxw[anc[u][i - 1]][i - 1]);
		lazy[u][i] = inf;
	}
	for (int i = 0; i < adj[u].size(); i++) {
		int v = adj[u][i].v;
		int w = adj[u][i].w;
		int id = adj[u][i].id;
		if (v == anc[u][0]) continue;
		anc[v][0] = u;
		maxw[v][0] = w;
		lazy[v][0] = inf;
		to_prt[v] = id;
		dep[v] = dep[u] + 1;
		dfs(v);
	}
}

void change(int u, int p, int d) {
	for (int i = logn; i >= 0; i--) {
		if (dep[u] - (1 << i) >= dep[p]) {
			lazy[u][i] = min(lazy[u][i], d);
			u = anc[u][i];
		}
	}
}

int cal_lca(int u, int v) {
	if (dep[u] < dep[v]) swap(u, v);
	for (int i = logn; i >= 0; i--) {
		if (dep[u] - (1 << i) >= dep[v]) u = anc[u][i];
	}
	if (u == v) return u;
	for (int i = logn; i >= 0; i--) {
		if (dep[u] - (1 << i) <= 0) continue;
		if (anc[u][i] != anc[v][i]) {
			u = anc[u][i];
			v = anc[v][i];
		}
	}
	return anc[u][0];
}

int cal_maxw(int u, int p) {
	int ans = 0;
	for (int i = logn; i >= 0; i--) {
		if (dep[u] - (1 << i) >= dep[p]) {
			ans = max(ans, maxw[u][i]);
			u = anc[u][i];
		}
	}
	return ans;
}


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

const int maxn = 200001;
const int logn = 21;
const int inf = 1e9 + 1;

struct edge {
	int u, v, w, id;
	edge() {}
	edge(int v, int w, int id) :v(v), w(w), id(id) {}
	edge(int u, int v, int w, int id) :u(u), v(v), w(w), id(id) {}
	bool operator <(const edge &e) const { return w < e.w; }
};

edge e[maxn];
vector<edge> adj[maxn];
int anc[maxn][logn];
int minw[maxn][logn];
int lazy[maxn][logn];
int to_prt[maxn];
int w[maxn];
int dep[maxn];
int ans[maxn];
bool is_on[maxn];
int n, m;

void kruskal();
void dfs(int u);
void change(int u, int p, int w);
int cal_lca(int u, int v);
int cal_minw(int u, int p);

int main() {
	scanf("%d%d", &n, &m);
	for (int i = 1; i <= m; i++) {
		int u, v, w;
		scanf("%d%d%d", &u, &v, &w);
		e[i] = edge(u, v, w, i);
	}
	kruskal();
	dep[1] = 1;
	dfs(1);
	for (int i = 1; i <= m; i++) {
		if (is_on[i]) continue;
		int lca = cal_lca(e[i].u, e[i].v);
		change(e[i].u, lca, e[i].w);
		change(e[i].v, lca, e[i].w);
		int cur = min(cal_minw(e[i].u, lca), cal_minw(e[i].v, lca));
		if (cur < inf) ans[e[i].id] = cur - 1;
		else ans[e[i].id] = -1;
	}
	for (int j = logn - 1; j >= 1; j--) {
		for (int i = 1; i <= n; i++) {
			if (dep[i] - (1 << j) <= 0) continue;
			lazy[i][j - 1] = min(lazy[i][j - 1], lazy[i][j]);
			lazy[anc[i][j - 1]][j - 1] = min(lazy[anc[i][j - 1]][j - 1], lazy[i][j]);
		}
	}
	for (int i = 2; i <= n; i++) {
		w[i] = lazy[i][0];
		if (w[i] < inf) ans[to_prt[i]] = w[i] - 1;
		else ans[to_prt[i]] = -1;
	}
	for (int i = 1; i <= m; i++) {
		printf("%d ", ans[i]);
	}
	return 0;
}

int p[maxn];

int find_root(int a) {
	if (p[a] == a) return a;
	return p[a] = find_root(p[a]);
}

void merge(int a, int b) {
	p[find_root(a)] = find_root(b);
}

void kruskal() {
	for (int i = 1; i <= n; i++) {
		p[i] = i;
	}
	sort(e + 1, e + 1 + m);
	for (int i = 1; i <= m; i++) {
		if (find_root(e[i].u) == find_root(e[i].v)) continue;
		merge(e[i].u, e[i].v);
		is_on[e[i].id] = 1;
		adj[e[i].u].push_back(edge(e[i].v, e[i].w, e[i].id));
		adj[e[i].v].push_back(edge(e[i].u, e[i].w, e[i].id));
	}
}

void dfs(int u) {
	for (int i = 1; i < logn; i++) {
		if (dep[u] - (1 << i) <= 0) continue;
		anc[u][i] = anc[anc[u][i - 1]][i - 1];
		minw[u][i] = min(minw[u][i - 1], minw[anc[u][i - 1]][i - 1]);
		lazy[u][i] = inf;
	}
	for (int i = 0; i < adj[u].size(); i++) {
		int v = adj[u][i].v;
		int w = adj[u][i].w;
		int id = adj[u][i].id;
		if (v == anc[u][0]) continue;
		anc[v][0] = u;
		minw[v][0] = w;
		lazy[v][0] = inf;
		to_prt[v] = id;
		dep[v] = dep[u] + 1;
		dfs(v);
	}
}

void change(int u, int p, int d) {
	for (int i = logn; i >= 0; i--) {
		if (dep[u] - (1 << i) >= dep[p]) {
			lazy[u][i] = min(lazy[u][i], d);
			u = anc[u][i];
		}
	}
}

int cal_lca(int u, int v) {
	if (dep[u] < dep[v]) swap(u, v);
	for (int i = logn; i >= 0; i--) {
		if (dep[u] - (1 << i) >= dep[v]) u = anc[u][i];
	}
	if (u == v) return u;
	for (int i = logn; i >= 0; i--) {
		if (dep[u] - (1 << i) <= 0) continue;
		if (anc[u][i] != anc[v][i]) {
			u = anc[u][i];
			v = anc[v][i];
		}
	}
	return anc[u][0];
}

int cal_minw(int u, int p) {
	int ans = inf;
	for (int i = logn; i >= 0; i--) {
		if (dep[u] - (1 << i) >= dep[p]) {
			ans = min(ans, minw[u][i]);
			u = anc[u][i];
		}
	}
	return ans;
}


#include<cstdio>
#include<iostream>
#include<cstdlib>
#include<algorithm>
#include<cmath>
#include<queue>
#include<ctime>
#define N 200003
#include<map>
#include<string>
#include<cstring>
using namespace std;
#define ll long long
#define mp make_pair
ll read()
{
	ll f=1,x=0;
	char c=getchar();
	while(c>'9'||c<'0')
	{
		if(c=='-') f=-1;
		c=getchar();
	}
	while(c>='0'&&c<='9')
	{
		x=x*10+c-'0';
		c=getchar();
	}
	return f*x;
}
int n,m,fa[N],st[N],re[N],num,as[N];
struct edge{
	int from,to,vlu,id;
}mem[N<<1];
struct LCT{
	int son[2],fa,mn,mx,vlu,add;
	bool rev;
}T[N<<2];
bool nroot(int x)
{
	return T[T[x].fa].son[0]==x||T[T[x].fa].son[1]==x;
}
void pushup(int x)
{
	int l=T[x].son[0],r=T[x].son[1];
	T[x].mx=max(T[l].mx,max(T[r].mx,T[x].vlu));
}
void pushdown(int x)
{
	int l=T[x].son[0],r=T[x].son[1];
	if(T[x].add!=2e9)
	{
		T[l].mn=min(T[l].mn,T[x].add);T[l].add=min(T[l].add,T[x].add);
		T[r].mn=min(T[r].mn,T[x].add);T[r].add=min(T[r].add,T[x].add);
		T[x].add=2e9;
	}
	if(T[x].rev)
	{
		T[x].rev=0;
		swap(T[l].son[0],T[l].son[1]);T[l].rev^=1;
		swap(T[r].son[1],T[r].son[0]);T[r].rev^=1;
	}
}
void fdown(int x)
{
	if(nroot(x)) fdown(T[x].fa);
	pushdown(x);
}
void rotate(int x)
{
	int y=T[x].fa,z=T[y].fa,p=x==T[y].son[1];
	T[y].son[p]=T[x].son[p^1];
	T[T[y].son[p]].fa=y;
	if(nroot(y)) T[z].son[T[z].son[1]==y]=x;
	T[x].fa=z;T[y].fa=x;T[x].son[p^1]=y;
	pushup(y),pushup(x);
}
void splay(int x)
{
	fdown(x);
	while(nroot(x))
	{
		int y=T[x].fa,z=T[y].fa;
		if(nroot(y))
		{
			if((x==T[y].son[1])^(y==T[z].son[0])) rotate(y),rotate(x);
			else rotate(x),rotate(x);
		}
		else rotate(x);
	}
}
void access(int x)
{
	int y=0;
	while(x)
	{
		splay(x);
		T[x].son[1]=y;
		pushup(x);
		x=T[y=x].fa;
	}
}
void mroot(int x)
{
	access(x);splay(x);T[x].rev^=1;swap(T[x].son[0],T[x].son[1]);
}
void link(int x,int y)
{
	mroot(x);T[x].fa=y;
}
bool cmp(edge a,edge b)
{
	return a.vlu<b.vlu;
}
int getfa(int x)
{
	return x==fa[x]?x:fa[x]=getfa(fa[x]);
}
int main()
{
	T[0].mx=-2e9;T[0].mn=2e9;
	n=read(),m=read();num=n;
	for(int i=1;i<=m;++i) mem[i].to=read(),mem[i].from=read(),mem[i].vlu=read(),mem[i].id=i;
	for(int i=1;i<=n;++i) fa[i]=i,T[i].mx=-2e9,T[i].mn=2e9;
	sort(mem+1,mem+1+m,cmp);
	for(int i=1;i<=m;++i)
	{
		int x=getfa(mem[i].from),y=getfa(mem[i].to);
		if(x!=y)
		{
			re[i]=++num;
			T[num].vlu=T[num].mx=mem[i].vlu;
			T[num].mn=2e9;
			link(num,mem[i].from),link(mem[i].to,num);
			fa[x]=y;
		}
	}
	for(int i=1;i<=m;++i) if(!re[i])
	{
		int x=mem[i].from,y=mem[i].to;
		mroot(x);access(y);splay(y);
		as[mem[i].id]=T[y].mx-1;
		T[y].add=min(T[y].add,mem[i].vlu);T[y].mn=min(T[y].mn,mem[i].vlu);
	}
	for(int i=1;i<=m;++i) if(re[i])
	{
	//	cout<<mem[i].id<<'\n';
		mroot(re[i]);
		if(T[re[i]].mn==2e9) as[mem[i].id]=-1;
		else as[mem[i].id]=T[re[i]].mn-1;
	}
	for(int i=1;i<=m;++i) cout<<as[i]<<" ";
	return 0;
}


#include<cstdio>
#include<iostream>
#include<cstdlib>
#include<algorithm>
#include<cmath>
#include<queue>
#include<ctime>
#define N 100003
#include<map>
#include<string>
#include<cstring>
using namespace std;
#define ll long long
#define mp make_pair
ll read()
{
	ll f=1,x=0;
	char c=getchar();
	while(c>'9'||c<'0')
	{
		if(c=='-') f=-1;
		c=getchar();
	}
	while(c>='0'&&c<='9')
	{
		x=x*10+c-'0';
		c=getchar();
	}
	return f*x;
}
int n,m,fa[N],st[N],re[N],num,as[N];
struct edge{
	int from,to,vlu,id;
}mem[N<<1];
struct LCT{
	int son[2],fa,mn,mx,vlu,add;
	bool rev;
}T[N<<2];
bool nroot(int x)
{
	return T[T[x].fa].son[0]==x||T[T[x].fa].son[1]==x;
}
void pushup(int x)
{
	int l=T[x].son[0],r=T[x].son[1];
	T[x].mx=max(T[l].mx,max(T[r].mx,T[x].vlu));
}
void pushdown(int x)
{
	int l=T[x].son[0],r=T[x].son[1];
	if(T[x].add!=2e9)
	{
		T[l].mn=min(T[l].mn,T[x].add);T[l].add=min(T[l].add,T[x].add);
		T[r].mn=min(T[r].mn,T[x].add);T[r].add=min(T[r].add,T[x].add);
		T[x].add=2e9;
	}
	if(T[x].rev)
	{
		T[x].rev=0;
		swap(T[l].son[0],T[l].son[1]);T[l].rev^=1;
		swap(T[r].son[1],T[r].son[0]);T[r].rev^=1;
	}
}
void fdown(int x)
{
	if(nroot(x)) fdown(T[x].fa);
	pushdown(x);
}
void rotate(int x)
{
	int y=T[x].fa,z=T[y].fa,p=x==T[y].son[1];
	T[y].son[p]=T[x].son[p^1];
	T[T[y].son[p]].fa=y;
	if(nroot(y)) T[z].son[T[z].son[1]==y]=x;
	T[x].fa=z;T[y].fa=x;T[x].son[p^1]=y;
	pushup(y),pushup(x);
}
void splay(int x)
{
	fdown(x);
	while(nroot(x))
	{
		int y=T[x].fa,z=T[y].fa;
		if(nroot(y))
		{
			if((x==T[y].son[1])^(y==T[z].son[0])) rotate(y),rotate(x);
			else rotate(x),rotate(x);
		}
		else rotate(x);
	}
}
void access(int x)
{
	int y=0;
	while(x)
	{
		splay(x);
		T[x].son[1]=y;
		pushup(x);
		x=T[y=x].fa;
	}
}
void mroot(int x)
{
	access(x);splay(x);T[x].rev^=1;swap(T[x].son[0],T[x].son[1]);
}
void link(int x,int y)
{
	mroot(x);T[x].fa=y;
}
bool cmp(edge a,edge b)
{
	return a.vlu<b.vlu;
}
int getfa(int x)
{
	return x==fa[x]?x:fa[x]=getfa(fa[x]);
}
int main()
{
	T[0].mx=-2e9;T[0].mn=2e9;
	n=read(),m=read();num=n;
	for(int i=1;i<=m;++i) mem[i].to=read(),mem[i].from=read(),mem[i].vlu=read(),mem[i].id=i;
	for(int i=1;i<=n;++i) fa[i]=i,T[i].mx=-2e9,T[i].mn=2e9;
	sort(mem+1,mem+1+m,cmp);
	for(int i=1;i<=m;++i)
	{
		int x=getfa(mem[i].from),y=getfa(mem[i].to);
		if(x!=y)
		{
			re[i]=++num;
			T[num].vlu=T[num].mx=mem[i].vlu;
			T[num].mn=2e9;
			link(num,mem[i].from),link(mem[i].to,num);
			fa[x]=y;
		}
	}
	for(int i=1;i<=m;++i) if(!re[i])
	{
		int x=mem[i].from,y=mem[i].to;
		mroot(x);access(y);splay(y);
		as[mem[i].id]=T[y].mx-1;
		T[y].add=min(T[y].add,mem[i].vlu);T[y].mn=min(T[y].mn,mem[i].vlu);
	}
	for(int i=1;i<=m;++i) if(re[i])
	{
	//	cout<<mem[i].id<<'\n';
		mroot(re[i]);
		if(T[re[i]].mn==2e9) as[mem[i].id]=-1;
		else as[mem[i].id]=T[re[i]].mn-1;
	}
	for(int i=1;i<=m;++i) cout<<as[i]<<" ";
	return 0;
}


#include<cstdio>
#include<iostream>
#include<cstdlib>
#include<algorithm>
#include<cmath>
#include<queue>
#include<ctime>
#define N 100003
#include<map>
#include<string>
#include<cstring>
using namespace std;
#define ll long long
#define mp make_pair
ll read()
{
	ll f=1,x=0;
	char c=getchar();
	while(c>'9'||c<'0')
	{
		if(c=='-') f=-1;
		c=getchar();
	}
	while(c>='0'&&c<='9')
	{
		x=x*10+c-'0';
		c=getchar();
	}
	return f*x;
}
int n,m,fa[N],st[N],re[N],num,as[N];
struct edge{
	int from,to,vlu,id;
}mem[N<<1];
struct LCT{
	int son[2],fa,mn,mx,vlu,add;
	bool rev;
}T[N<<2];
bool nroot(int x)
{
	return T[T[x].fa].son[0]==x||T[T[x].fa].son[1]==x;
}
void pushup(int x)
{
	int l=T[x].son[0],r=T[x].son[1];
	T[x].mx=max(T[l].mx,max(T[r].mx,T[x].vlu));
}
void pushdown(int x)
{
	int l=T[x].son[0],r=T[x].son[1];
	if(T[x].add!=2e9)
	{
		T[l].mn=min(T[l].mn,T[x].add);T[l].add=min(T[l].add,T[x].add);
		T[r].mn=min(T[r].mn,T[x].add);T[r].add=min(T[r].add,T[x].add);
		T[x].add=2e9;
	}
	if(T[x].rev)
	{
		T[x].rev=0;
		swap(T[l].son[0],T[l].son[1]);T[l].rev^=1;
		swap(T[r].son[1],T[r].son[0]);T[r].rev^=1;
	}
}
void fdown(int x)
{
	if(nroot(x)) fdown(T[x].fa);
	pushdown(x);
}
void rotate(int x)
{
	int y=T[x].fa,z=T[y].fa,p=x==T[y].son[1];
	T[y].son[p]=T[x].son[p^1];
	T[T[y].son[p]].fa=y;
	if(nroot(y)) T[z].son[T[z].son[1]==y]=x;
	T[x].fa=z;T[y].fa=x;T[x].son[p^1]=y;
	pushup(y),pushup(x);
}
void splay(int x)
{
	fdown(x);
	while(nroot(x))
	{
		int y=T[x].fa,z=T[y].fa;
		if(nroot(y))
		{
			if((x==T[y].son[1])^(y==T[z].son[0])) rotate(y),rotate(x);
			else rotate(x),rotate(x);
		}
		else rotate(x);
	}
}
void access(int x)
{
	int y=0;
	while(x)
	{
		splay(x);
		T[x].son[1]=y;
		pushup(y);
		x=T[y=x].fa;
	}
}
void mroot(int x)
{
	access(x);splay(x);T[x].rev^=1;swap(T[x].son[0],T[x].son[1]);
}
void link(int x,int y)
{
	mroot(x);T[x].fa=y;
}
bool cmp(edge a,edge b)
{
	return a.vlu<b.vlu;
}
int getfa(int x)
{
	return x==fa[x]?x:fa[x]=getfa(fa[x]);
}
int main()
{
	T[0].mx=-2e9;T[0].mn=2e9;
	n=read(),m=read();num=n;
	for(int i=1;i<=m;++i) mem[i].to=read(),mem[i].from=read(),mem[i].vlu=read(),mem[i].id=i;
	for(int i=1;i<=n;++i) fa[i]=i,T[i].mx=-2e9,T[i].mn=2e9;
	sort(mem+1,mem+1+m,cmp);
	for(int i=1;i<=m;++i)
	{
		int x=getfa(mem[i].from),y=getfa(mem[i].to);
		if(x!=y)
		{
			re[i]=++num;
			T[num].vlu=T[num].mx=mem[i].vlu;
			T[num].mn=2e9;
			link(num,mem[i].from),link(mem[i].to,num);
			fa[x]=y;
		}
	}
	for(int i=1;i<=m;++i) if(!re[i])
	{
		int x=mem[i].from,y=mem[i].to;
		mroot(x);access(y);splay(y);
		as[mem[i].id]=T[y].mx-1;
		T[y].add=min(T[y].add,mem[i].vlu);T[y].mn=min(T[y].mn,mem[i].vlu);
	}
	for(int i=1;i<=m;++i) if(re[i])
	{
	//	cout<<mem[i].id<<'\n';
		mroot(re[i]);
		if(T[re[i]].mn==2e9) as[mem[i].id]=-1;
		else as[mem[i].id]=T[re[i]].mn-1;
	}
	for(int i=1;i<=m;++i) cout<<as[i]<<" ";
	return 0;
}


#include <bits/stdc++.h>
#define FOR(i, u, v) for (int i = u; i <= v; i++)
#define FORD(i, v, u) for (int i = v; i >= u; i--)
#define pii pair<int, int>
#define mp make_pair
#define F first
#define S second
#define PB push_back
#define N 200005
#define LN 19
#define maxc 1000000007
#define ll long long

using namespace std;

struct edge
{
    int u, v, w, id;
    edge(int _u=0, int _v=0, int _w=0, int _id=0) : u(_u), v(_v), w(_w), id(_id) {}
    bool operator < (const edge &rhs) const
    {
        return w < rhs.w;
    }
}e[N];

int n, m;
map<pii, int> maId;

void setup()
{
    cin >> n >> m;
    FOR(i, 1, m)
    {
        int u, v, w; cin >> u >> v >> w;
        maId[mp(u, v)] = maId[mp(v, u)] = i;
        e[i] = {u, v, w, i};
    }
}
int inMST[N], root[N];
vector<pii> g[N];
int get_root(int u)
{
    return (root[u] == 0) ? u : root[u] = get_root(root[u]);
}
void buildMST()
{
    sort(e+1, e+m+1);
    FOR(i, 1, m)
    {
        int u = e[i].u, v = e[i].v, w = e[i].w, id = e[i].id;
        int p = get_root(u);
        int q = get_root(v);
        if (p == q) continue;

        inMST[id] = 1;
        root[p] = q;
        g[u].PB(mp(v, w)); g[v].PB(mp(u, w));
    }
}
int in[N];
int h[N], p[N][LN], wMin[N][LN];
void DFSMST(int u)
{
    for (auto z : g[u])
    {
        int v = z.F;
        int w = z.S;
        if (v == p[u][0]) continue;
        in[u]++;
        h[v] = h[u] + 1;
        p[v][0] = u;
        wMin[v][0] = w;
        FOR(i, 1, LN-1)
        {
            p[v][i] = p[p[v][i-1]][i-1];
            wMin[v][i] = max(wMin[v][i-1], wMin[p[v][i-1]][i-1]);
        }
        DFSMST(v);
    }
}
pii getMinPath(int u, int v)
{
    int ans = 0;

    if (h[u] > h[v]) swap(u, v);
    int delta = h[v] - h[u];
    FOR(i, 0, LN-1)
        if ((delta >> i) & 1)
        {
            ans = max(ans, wMin[v][i]);
            v = p[v][i];
        }
    if (u == v) return mp(u, ans);
    FORD(i, LN-1, 0)
        if (p[u][i] != p[v][i])
        {
            ans = max({ans, wMin[u][i], wMin[v][i]});
            u = p[u][i];
            v = p[v][i];
        }
    return mp(p[u][0], max({ans, wMin[u][0], wMin[v][0]}));
}
int res[N];

void solveType1()
{
    FOR(i, 1, m)
    {
        int u = e[i].u, v = e[i].v, id = e[i].id;
        if (inMST[id]) continue;
        res[id] = getMinPath(u, v).S-1;
    }
}
set<pii> s[N];

void Merge(int u, int v)
{
    if (s[u].size() < s[v].size()) swap(s[u], s[v]);
    for (auto z : s[v])
        s[u].insert(z);
}
vector<pii> delE[N];

void prepareType2()
{
    FOR(i, 1, m)
    {
        int u = e[i].u, v = e[i].v, w = e[i].w, id = e[i].id;
        if (inMST[id]) continue;
        int lca = getMinPath(u, v).F;
        s[u].insert(mp(w, id));
        s[v].insert(mp(w, id));
        delE[lca].PB(mp(w, id));
    }
}
void solveType2()
{
    queue<int> q;
    FOR(i, 1, n)
        if (in[i] == 0) q.push(i);
    while (!q.empty())
    {
        int u = q.front(); q.pop();
        /*if (u == 9)
            for (auto z : s[u]) cerr <<(z).F<<' '<<(z).S<<' ';
        cout <<endl;*/
        for (auto z : delE[u])
        {
            //cerr<<e[idE].w<<' '<<idE<<endl;
            s[u].erase(z);
        }
        int v = p[u][0];
        int w = wMin[u][0];
        int id = maId[mp(u, v)];

        if (s[u].empty()) res[id] = -1;
        else
        {
            int ww = (*s[u].begin()).F;
            res[id] = ww-1;

        }
        Merge(v, u);
        in[v]--;
        if (in[v] == 0) q.push(v);
    }
}
int main()
{
    ios_base::sync_with_stdio(0); cin.tie(0); cout.tie(0);
    //freopen("INP.TXT", "r", stdin);
    setup();
    buildMST();
    DFSMST(1);
    solveType1();
    prepareType2();
    solveType2();
    FOR(i, 1, m)
        cout <<res[i]<<' ';
}


#include <bits/stdc++.h>
#define FOR(i, u, v) for (int i = u; i <= v; i++)
#define FORD(i, v, u) for (int i = v; i >= u; i--)
#define pii pair<int, int>
#define mp make_pair
#define F first
#define S second
#define PB push_back
#define N 200005
#define LN 19
#define maxc 1000000007
#define ll long long

using namespace std;

struct edge
{
    int u, v, w, id;
    edge(int _u=0, int _v=0, int _w=0, int _id=0) : u(_u), v(_v), w(_w), id(_id) {}
    bool operator < (const edge &rhs) const
    {
        return w < rhs.w;
    }
}e[N];

int n, m;
map<pii, int> maId;

void setup()
{
    cin >> n >> m;
    FOR(i, 1, m)
    {
        int u, v, w; cin >> u >> v >> w;
        maId[mp(u, v)] = i;
        e[i] = {u, v, w, i};
    }
}
int inMST[N], root[N];
vector<pii> g[N];
int get_root(int u)
{
    return (root[u] == 0) ? u : root[u] = get_root(root[u]);
}
void buildMST()
{
    sort(e+1, e+m+1);
    FOR(i, 1, m)
    {
        int u = e[i].u, v = e[i].v, w = e[i].w, id = e[i].id;
        int p = get_root(u);
        int q = get_root(v);
        if (p == q) continue;

        inMST[id] = 1;
        root[p] = q;
        g[u].PB(mp(v, w)); g[v].PB(mp(u, w));
    }
}
int in[N], idPa[N];
int h[N], p[N][LN], wMin[N][LN];
void DFSMST(int u)
{
    for (auto z : g[u])
    {
        int v = z.F;
        int w = z.S;
        if (v == p[u][0]) continue;
        in[u]++;
        idPa[v] = maId[mp(u, v)];
        h[v] = h[u] + 1;
        p[v][0] = u;
        wMin[v][0] = w;
        FOR(i, 1, LN-1)
        {
            p[v][i] = p[p[v][i-1]][i-1];
            wMin[v][i] = min(wMin[v][i-1], wMin[p[v][i-1]][i-1]);
        }
        DFSMST(v);
    }
}
pii getMinPath(int u, int v)
{
    int ans = maxc;

    if (h[u] > h[v]) swap(u, v);
    int delta = h[v] - h[u];
    FOR(i, 0, LN-1)
        if ((delta >> i) & 1)
        {
            ans = min(ans, wMin[v][i]);
            v = p[v][i];
        }
    if (u == v) return mp(u, ans);
    FORD(i, LN-1, 0)
        if (p[u][i] != p[v][i])
        {
            ans = min({ans, wMin[u][i], wMin[v][i]});
            u = p[u][i];
            v = p[v][i];
        }
    return mp(p[u][0], min({ans, wMin[u][0], wMin[v][0]}));
}
int res[N];

void solveType1()
{
    FOR(i, 1, m)
    {
        int u = e[i].u, v = e[i].v, id = e[i].id;
        if (inMST[id]) continue;
        res[id] = getMinPath(u, v).S-1;
    }
}
set<pii> s[N];

void Merge(int u, int v)
{
    if (s[u].size() < s[v].size()) swap(s[u], s[v]);
    for (auto z : s[v])
        s[u].insert(z);
}
vector<int> delE[N];

void prepareType2()
{
    FOR(i, 1, m)
    {
        int u = e[i].u, v = e[i].v, w = e[i].w, id = e[i].id;
        if (inMST[id]) continue;
        int lca = getMinPath(u, v).F;
        s[u].insert(mp(w, id));
        s[v].insert(mp(w, id));
        delE[lca].PB(id);
    }
}
void solveType2()
{
    queue<int> q;
    FOR(i, 2, n)
        if (in[i] == 0) q.push(i);
    while (!q.empty())
    {
        int u = q.front(); q.pop();
        for (auto idE : delE[u])
            s[u].erase(mp(e[idE].w, idE));
        int v = p[u][0];
        int w = wMin[u][0];
        int id = idPa[u];

        if (s[u].empty()) res[id] = -1;
        else
        {
            int ww = (*s[u].begin()).F;
            if (ww > w) res[id] = w;
            else res[id] = w-1;
        }

        Merge(v, u);
        in[v]--;
        if (in[v] == 0) q.push(v);
    }
}
int main()
{
    ios_base::sync_with_stdio(0); cin.tie(0); cout.tie(0);
    //freopen("INP.TXT", "r", stdin);
    setup();
    buildMST();
    DFSMST(1);
    solveType1();
    prepareType2();
    solveType2();
    FOR(i, 1, m)
        cout <<res[i]<<' ';
}


#include <bits/stdc++.h>
#define FOR(i, u, v) for (int i = u; i <= v; i++)
#define FORD(i, v, u) for (int i = v; i >= u; i--)
#define pii pair<int, int>
#define mp make_pair
#define F first
#define S second
#define PB push_back
#define N 200005
#define LN 19
#define maxc 1000000007
#define ll long long

using namespace std;

struct edge
{
    int u, v, w, id;
    edge(int _u=0, int _v=0, int _w=0, int _id=0) : u(_u), v(_v), w(_w), id(_id) {}
    bool operator < (const edge &rhs) const
    {
        return w < rhs.w;
    }
}e[N];

int n, m;
map<pii, int> maId;

void setup()
{
    cin >> n >> m;
    FOR(i, 1, m)
    {
        int u, v, w; cin >> u >> v >> w;
        maId[mp(u, v)] = maId[mp(v, u)] = i;
        e[i] = {u, v, w, i};
    }
}
int inMST[N], root[N];
vector<pii> g[N];
int get_root(int u)
{
    return (root[u] == 0) ? u : root[u] = get_root(root[u]);
}
void buildMST()
{
    sort(e+1, e+m+1);
    FOR(i, 1, m)
    {
        int u = e[i].u, v = e[i].v, w = e[i].w, id = e[i].id;
        int p = get_root(u);
        int q = get_root(v);
        if (p == q) continue;

        inMST[id] = 1;
        root[p] = q;
        g[u].PB(mp(v, w)); g[v].PB(mp(u, w));
    }
}
int in[N], idPa[N];
int h[N], p[N][LN], wMin[N][LN];
void DFSMST(int u)
{
    for (auto z : g[u])
    {
        int v = z.F;
        int w = z.S;
        if (v == p[u][0]) continue;
        in[u]++;
        idPa[v] = maId[mp(u, v)];
        h[v] = h[u] + 1;
        p[v][0] = u;
        wMin[v][0] = w;
        FOR(i, 1, LN-1)
        {
            p[v][i] = p[p[v][i-1]][i-1];
            wMin[v][i] = max(wMin[v][i-1], wMin[p[v][i-1]][i-1]);
        }
        DFSMST(v);
    }
}
pii getMinPath(int u, int v)
{
    int ans = 0;

    if (h[u] > h[v]) swap(u, v);
    int delta = h[v] - h[u];
    FOR(i, 0, LN-1)
        if ((delta >> i) & 1)
        {
            ans = max(ans, wMin[v][i]);
            v = p[v][i];
        }
    if (u == v) return mp(u, ans);
    FORD(i, LN-1, 0)
        if (p[u][i] != p[v][i])
        {
            ans = max({ans, wMin[u][i], wMin[v][i]});
            u = p[u][i];
            v = p[v][i];
        }
    return mp(p[u][0], max({ans, wMin[u][0], wMin[v][0]}));
}
int res[N];

void solveType1()
{
    FOR(i, 1, m)
    {
        int u = e[i].u, v = e[i].v, id = e[i].id;
        if (inMST[id]) continue;
        res[id] = getMinPath(u, v).S-1;
    }
}
set<pii> s[N];

void Merge(int u, int v)
{
    if (s[u].size() < s[v].size()) swap(s[u], s[v]);
    for (auto z : s[v])
        s[u].insert(z);
}
vector<int> delE[N];

void prepareType2()
{
    FOR(i, 1, m)
    {
        int u = e[i].u, v = e[i].v, w = e[i].w, id = e[i].id;
        if (inMST[id]) continue;
        int lca = getMinPath(u, v).F;
        s[u].insert(mp(w, id));
        s[v].insert(mp(w, id));
        delE[lca].PB(id);
    }
}
void solveType2()
{
    queue<int> q;
    FOR(i, 1, n)
        if (in[i] == 0) q.push(i);
    while (!q.empty())
    {
        int u = q.front(); q.pop();
        for (auto idE : delE[u])
            s[u].erase(mp(e[idE].w, idE));
        int v = p[u][0];
        int w = wMin[u][0];
        int id = idPa[u];

        if (s[u].empty()) res[id] = -1;
        else
        {
            int ww = (*s[u].begin()).F;
            res[id] = ww-1;

        }

        Merge(v, u);
        in[v]--;
        if (in[v] == 0) q.push(v);
    }
}
int main()
{
    ios_base::sync_with_stdio(0); cin.tie(0); cout.tie(0);
    //freopen("INP.TXT", "r", stdin);
    setup();
    buildMST();
    DFSMST(1);
    solveType1();
    prepareType2();
    solveType2();
    FOR(i, 1, m)
        cout <<res[i]<<' ';
}


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

namespace zuiyt
{
	const int N = 2e5 + 10, M = 2e5 + 10, B = 20, INF = 0x3f3f3f3f;
	int n, m;
	struct ed
	{
		int u, v, w, id;
		bool in_tree;
		bool operator < (const ed &b) const
		{
			return w < b.w;
		}
	}e[M];
	struct edge
	{
		int to, w, id;
	};
	vector<edge> g[N];
	int p[N], pre[N], dep[N], maxx[N][B], minn[N][B], fa[N][B], ans[M];
	int f(const int x)
	{
		return x == p[x] ? x : p[x] = f(p[x]);
	}
	void dfs(const int u, const int f)
	{
		dep[u] = dep[f] + 1;
		fa[u][0] = f;
		for (int i = 1; i < B; i++)
		{
			fa[u][i] = fa[fa[u][i - 1]][i - 1];
			maxx[u][i] = max(maxx[u][i - 1], maxx[fa[u][i - 1]][i - 1]);
		}
		for (int i = 0; i < g[u].size(); i++)
		{
			int v = g[u][i].to;
			if (v == f)
				continue;
			pre[v] = g[u][i].id;
			maxx[v][0] = g[u][i].w;
			dfs(v, u);
		}
	}
	int query_max(int a, int b)
	{
		int ans = 0;
		if (dep[a] < dep[b])
			swap(a, b);
		for (int i = B - 1; i >= 0; i--)
			if (dep[fa[a][i]] >= dep[b])
				ans = max(ans, maxx[a][i]), a = fa[a][i];
		if (a == b)
			return ans;
		for (int i = B - 1; i >= 0; i--)
			if (fa[a][i] != fa[b][i])
			{
				ans = max(ans, max(maxx[a][i], maxx[b][i]));
				a = fa[a][i], b = fa[b][i];
			}
		return max(ans, max(maxx[a][0], maxx[b][0]));
	}
	void change_min(int a, int b, const int w)
	{
		if (dep[a] < dep[b])
			swap(a, b);
		for (int i = B - 1; i >= 0; i--)
			if (dep[fa[a][i]] >= dep[b])
				minn[a][i] = min(minn[a][i], w), a = fa[a][i];
		if (a == b)
			return;
		for (int i = B - 1; i >= 0; i--)
			if (fa[a][i] != fa[b][i])
			{
				minn[a][i] = min(minn[a][i], w);
				minn[b][i] = min(minn[b][i], w);
				a = fa[a][i];
				b = fa[b][i];
			}
		minn[a][0] = min(minn[a][0], w);
		minn[b][0] = min(minn[b][0], w);
	}
	void Kruskal()
	{
		for (int i = 1; i <= n; i++)
			p[i] = i;
		for (int i = 0; i < m; i++)
		{
			int u = e[i].u, v = e[i].v, x = f(u), y = f(v);
			if (x != y)
			{
				p[x] = y;
				g[u].push_back((edge){v, e[i].w, e[i].id});
				g[v].push_back((edge){u, e[i].w, e[i].id});
				e[i].in_tree = true;
			}
		}
	}
	int work()
	{
		ios::sync_with_stdio(false);
		cin.tie(0);
		cin >> n >> m;
		memset(minn, INF, sizeof(int[n + 1][B]));
		for (int i = 0; i < m; i++)
		{
			cin >> e[i].u >> e[i].v >> e[i].w;
			e[i].id = i;
		}
		sort(e, e + m);
		Kruskal();
		dfs(1, 0);
		for (int i = 0; i < m; i++)
			if (!e[i].in_tree)
			{
				ans[e[i].id] = query_max(e[i].u, e[i].v) - 1;
				change_min(e[i].u, e[i].v, e[i].w);
			}
		for (int j = B - 1; j > 0; j--)
			for (int i = 1; i <= n; i++)
			{
				minn[i][j - 1] = min(minn[i][j - 1], minn[i][j]);
				minn[fa[i][j - 1]][j - 1] = min(minn[fa[i][j - 1]][j - 1], minn[i][j]);
			}
		for (int i = 2; i <= n; i++)
			ans[pre[i]] = minn[i][0] - 1;
		for (int i = 0; i < m; i++)
			if (ans[i] < INF - 1)
				cout << ans[i] << ' ';
			else
				cout << "-1 ";
		return 0;
	}
}
int main()
{
	return zyt::work();
}


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

namespace zyt
{
	const int N = 2e5 + 10, M = 2e5 + 10, B = 20, INF = 0x3f3f3f3f;
	int n, m;
	struct ed
	{
		int u, v, w, id;
		bool in_tree;
		bool operator < (const ed &b) const
		{
			return w < b.w;
		}
	}e[M];
	struct edge
	{
		int to, w, id;
	};
	vector<edge> g[N];
	int p[N], pre[N], dep[N], maxx[N][B], minn[N][B], fa[N][B], ans[M];
	int f(const int x)
	{
		return x == p[x] ? x : p[x] = f(p[x]);
	}
	void dfs(const int u, const int f)
	{
		dep[u] = dep[f] + 1;
		fa[u][0] = f;
		for (int i = 1; i < B; i++)
		{
			fa[u][i] = fa[fa[u][i - 1]][i - 1];
			maxx[u][i] = max(maxx[u][i - 1], maxx[fa[u][i - 1]][i - 1]);
		}
		for (int i = 0; i < g[u].size(); i++)
		{
			int v = g[u][i].to;
			if (v == f)
				continue;
			pre[v] = g[u][i].id;
			maxx[v][0] = g[u][i].w;
			dfs(v, u);
		}
	}
	int query_max(int a, int b)
	{
		int ans = 0;
		if (dep[a] < dep[b])
			swap(a, b);
		for (int i = B - 1; i >= 0; i--)
			if (dep[fa[a][i]] >= dep[b])
				ans = max(ans, maxx[a][i]), a = fa[a][i];
		if (a == b)
			return ans;
		for (int i = B - 1; i >= 0; i--)
			if (fa[a][i] != fa[b][i])
			{
				ans = max(ans, max(maxx[a][i], maxx[b][i]));
				a = fa[a][i], b = fa[b][i];
			}
		return max(ans, max(maxx[a][0], maxx[b][0]));
	}
	void change_min(int a, int b, const int w)
	{
		if (dep[a] < dep[b])
			swap(a, b);
		for (int i = B - 1; i >= 0; i--)
			if (dep[fa[a][i]] >= dep[b])
				minn[a][i] = min(minn[a][i], w), a = fa[a][i];
		if (a == b)
			return;
		for (int i = B - 1; i >= 0; i--)
			if (fa[a][i] != fa[b][i])
			{
				minn[a][i] = min(minn[a][i], w);
				minn[b][i] = min(minn[b][i], w);
				a = fa[a][i];
				b = fa[b][i];
			}
		minn[a][0] = min(minn[a][0], w);
		minn[b][0] = min(minn[b][0], w);
	}
	void Kruskal()
	{
		for (int i = 1; i <= n; i++)
			p[i] = i;
		for (int i = 0; i < m; i++)
		{
			int u = e[i].u, v = e[i].v, x = f(u), y = f(v);
			if (x != y)
			{
				p[x] = y;
				g[u].push_back((edge){v, e[i].w, e[i].id});
				g[v].push_back((edge){u, e[i].w, e[i].id});
				e[i].in_tree = true;
			}
		}
	}
	int work()
	{
		ios::sync_with_stdio(false);
		cin.tie(0);
		cin >> n >> m;
		memset(minn, INF, sizeof(int[n + 1][B]));
		for (int i = 0; i < m; i++)
		{
			cin >> e[i].u >> e[i].v >> e[i].w;
			e[i].id = i;
		}
		sort(e, e + m);
		Kruskal();
		dfs(1, 0);
		for (int i = 0; i < m; i++)
			if (!e[i].in_tree)
			{
				ans[e[i].id] = query_max(e[i].u, e[i].v) - 1;
				change_min(e[i].u, e[i].v, e[i].w);
			}
		for (int i = 1; i <= n; i++)
			for (int j = B - 1; j > 0; j--)
			{
				minn[i][j - 1] = min(minn[i][j - 1], minn[i][j]);
				minn[fa[i][j - 1]][j - 1] = min(minn[fa[i][j - 1]][j - 1], minn[i][j]);
			}
		for (int i = 2; i <= n; i++)
			ans[pre[i]] = minn[i][0] - 1;
		for (int i = 0; i < m; i++)
			if (ans[i] < INF - 1)
				cout << ans[i] << ' ';
			else
				cout << "-1 ";
		return 0;
	}
}
int main()
{
	return zyt::work();
}


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

namespace zyt
{
	const int N = 2e5 + 10, M = 2e5 + 10, B = 20, INF = 0x3f3f3f3f;
	int n, m;
	struct ed
	{
		int u, v, w, id;
		bool in_tree;
		bool operator < (const ed &b) const
		{
			return w < b.w;
		}
	}e[M];
	struct edge
	{
		int to, w, id;
	};
	vector<edge> g[N];
	int p[N], pre[N], dep[N], maxx[N][B], minn[N][B], fa[N][B], ans[M];
	int f(const int x)
	{
		return x == p[x] ? x : p[x] = f(p[x]);
	}
	void dfs(const int u, const int f)
	{
		dep[u] = dep[f] + 1;
		fa[u][0] = f;
		for (int i = 1; i < B; i++)
		{
			fa[u][i] = fa[fa[u][i - 1]][i - 1];
			maxx[u][i] = max(maxx[u][i - 1], maxx[fa[u][i - 1]][i - 1]);
		}
		for (int i = 0; i < g[u].size(); i++)
		{
			int v = g[u][i].to;
			if (v == f)
				continue;
			pre[v] = g[u][i].id;
			maxx[v][0] = g[u][i].w;
			dfs(v, u);
		}
	}
	int query_max(int a, int b)
	{
		int ans = 0;
		if (dep[a] < dep[b])
			swap(a, b);
		for (int i = B - 1; i >= 0; i--)
			if (dep[fa[a][i]] >= dep[b])
				ans = max(ans, maxx[a][i]), a = fa[a][i];
		if (a == b)
			return ans;
		for (int i = B - 1; i >= 0; i--)
			if (fa[a][i] != fa[b][i])
			{
				ans = max(ans, max(maxx[a][i], maxx[b][i]));
				a = fa[a][i], b = fa[b][i];
			}
		return max(ans, max(maxx[a][0], maxx[b][0]));
	}
	void change_min(int a, int b, const int w)
	{
		if (dep[a] < dep[b])
			swap(a, b);
		for (int i = B - 1; i >= 0; i--)
			if (dep[fa[a][i]] >= dep[b])
				minn[a][i] = min(minn[a][i], w), a = fa[a][i];
		if (a == b)
			return;
		for (int i = B - 1; i >= 0; i--)
			if (fa[a][i] != fa[b][i])
			{
				minn[a][i] = min(minn[a][i], w);
				minn[b][i] = min(minn[b][i], w);
				a = fa[a][i];
				b = fa[b][i];
			}
		minn[a][0] = min(minn[a][0], w);
		minn[b][0] = min(minn[b][0], w);
	}
	void Kruskal()
	{
		for (int i = 1; i <= n; i++)
			p[i] = i;
		for (int i = 0; i < m; i++)
		{
			int u = e[i].u, v = e[i].v, x = f(u), y = f(v);
			if (x != y)
			{
				p[x] = y;
				g[u].push_back((edge){v, e[i].w, e[i].id});
				g[v].push_back((edge){u, e[i].w, e[i].id});
				e[i].in_tree = true;
			}
		}
	}
	int work()
	{
		ios::sync_with_stdio(false);
		cin.tie(0);
		cin >> n >> m;
		memset(minn, INF, sizeof(int[n + 1][B]));
		for (int i = 0; i < m; i++)
		{
			cin >> e[i].u >> e[i].v >> e[i].w;
			e[i].id = i;
		}
		sort(e, e + m);
		Kruskal();
		dfs(1, 0);
		for (int i = 0; i < m; i++)
			if (!e[i].in_tree)
			{
				ans[e[i].id] = query_max(e[i].u, e[i].v) - 1;
				change_min(e[i].u, e[i].v, e[i].w);
			}
		for (int j = B - 1; j > 0; j--)
			for (int i = 1; i <= n; i++)
			{
				minn[i][j - 1] = min(minn[i][j - 1], minn[i][j]);
				minn[fa[i][j - 1]][j - 1] = min(minn[fa[i][j - 1]][j - 1], minn[i][j]);
			}
		for (int i = 2; i <= n; i++)
			ans[pre[i]] = minn[i][0] - 1;
		for (int i = 0; i < m; i++)
			if (ans[i] < INF - 1)
				cout << ans[i] << ' ';
			else
				cout << "-1 ";
		return 0;
	}
}
int main()
{
	return zyt::work();
}


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

namespace zyt
{
	const int N = 2e5 + 10, M = 2e5 + 10, B = 20, INF = 0x3f3f3f3f;
	int n, m;
	struct ed
	{
		int u, v, w, id;
		bool in_tree;
		bool operator < (const ed &b) const
		{
			return w < b.w;
		}
	}e[M];
	struct edge
	{
		int to, w, id;
	};
	vector<edge> g[N];
	int p[N], pre[N], dep[N], maxx[N][B], minn[N][B], fa[N][B], ans[M];
	int f(const int x)
	{
		return x == p[x] ? x : p[x] = f(p[x]);
	}
	void dfs(const int u, const int f)
	{
		dep[u] = dep[f] + 1;
		fa[u][0] = f;
		for (int i = 1; i < B; i++)
		{
			fa[u][i] = fa[fa[u][i - 1]][i - 1];
			maxx[u][i] = max(maxx[u][i - 1], maxx[fa[u][i - 1]][i - 1]);
		}
		for (int i = 0; i < g[u].size(); i++)
		{
			int v = g[u][i].to;
			if (v == f)
				continue;
			pre[v] = g[u][i].id;
			maxx[v][0] = g[u][i].w;
			dfs(v, u);
		}
	}
	int query_max(int a, int b)
	{
		int ans = 0;
		if (dep[a] < dep[b])
			swap(a, b);
		for (int i = B - 1; i >= 0; i--)
			if (dep[fa[a][i]] >= dep[b])
				ans = max(ans, maxx[a][i]), a = fa[a][i];
		if (a == b)
			return ans;
		for (int i = B - 1; i >= 0; i--)
			if (fa[a][i] != fa[b][i])
			{
				ans = max(ans, max(maxx[a][i], maxx[b][i]));
				a = fa[a][i], b = fa[b][i];
			}
		return max(ans, max(maxx[a][0], maxx[b][0]));
	}
	void change_min(int a, int b, const int w)
	{
		if (dep[a] < dep[b])
			swap(a, b);
		for (int i = B - 1; i >= 0; i--)
			if (dep[fa[a][i]] >= dep[b])
				minn[a][i] = min(minn[a][i], w), a = fa[a][i];
		if (a == b)
			return;
		for (int i = B - 1; i >= 0; i--)
			if (fa[a][i] != fa[b][i])
			{
				minn[a][i] = min(minn[a][i], w);
				minn[b][i] = min(minn[b][i], w);
				a = fa[a][i];
				b = fa[b][i];
			}
		minn[a][0] = min(minn[a][0], w);
		minn[b][0] = min(minn[b][0], w);
	}
	void Kruskal()
	{
		for (int i = 1; i <= n; i++)
			p[i] = i;
		for (int i = 0; i < m; i++)
		{
			int u = e[i].u, v = e[i].v, x = f(u), y = f(v);
			if (x != y)
			{
				p[x] = y;
				g[u].push_back((edge){v, e[i].w, e[i].id});
				g[v].push_back((edge){u, e[i].w, e[i].id});
				e[i].in_tree = true;
			}
		}
	}
	int work()
	{
		ios::sync_with_stdio(false);
		cin.tie(0);
		cin >> n >> m;
		memset(minn, INF, sizeof(int[n + 1][B]));
		for (int i = 0; i < m; i++)
		{
			cin >> e[i].u >> e[i].v >> e[i].w;
			e[i].id = i;
		}
		sort(e, e + m);
		Kruskal();
		dfs(1, 0);
		for (int i = 0; i < m; i++)
			if (!e[i].in_tree)
			{
				ans[e[i].id] = query_max(e[i].u, e[i].v) - 1;
				change_min(e[i].u, e[i].v, e[i].w);
			}
		for (int i = 1; i <= n; i++)
			for (int j = B - 1; j > 0; j--)
			{
				minn[i][j - 1] = min(minn[i][j - 1], minn[i][j]);
				minn[fa[i][j - 1]][j - 1] = min(minn[fa[i][j - 1]][j - 1], minn[i][j]);
			}
		for (int i = 1; i <= n; i++)
			ans[pre[i]] = minn[i][0] - 1;
		for (int i = 0; i < m; i++)
			if (ans[i] < INF - 1)
				cout << ans[i] << ' ';
			else
				cout << "-1 ";
		return 0;
	}
}
int main()
{
	return zyt::work();
}


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

namespace zyt
{
	const int N = 2e5 + 10, M = 2e5 + 10, B = 20, INF = 0x3f3f3f3f;
	int n, m;
	struct ed
	{
		int u, v, w, id;
		bool in_tree;
		bool operator < (const ed &b) const
		{
			return w < b.w;
		}
	}e[M];
	struct edge
	{
		int to, w, id;
	};
	vector<edge> g[N];
	int p[N], pre[N], dep[N], w[N], son[N], size[N], dfn[N], top[N], cnt;
	int f(const int x)
	{
		return x == p[x] ? x : p[x] = f(p[x]);
	}
	namespace Tree_Chain_Cut
	{
		void dfs1(const int u, const int f)
		{
			dep[u] = dep[f] + 1;
			fa[u] = f;
			size[u] = 1;
			for (int i = 0; i < g[u].size(); i++)
			{
				int v = g[u][i].to;
				if (v == f)
					continue;
				pre[v] = g[u][i].id;
				w[v] = g[u][i].w;
				dfs1(v, u);
				if (size[v] > size[son[u]])
					son[u] = v;
			}
		}
		void dfs2(const int u, const int t)
		{
			dfn[u] = ++cnt;
			top[u] = t;
			if (son[u])
				dfs2(son[u], t);
			for (int i = 0; i < g[u].size(); i++)
			{
				int v = g[u][i].to;
				if (dfn[v])
					continue;
				dfs2(v, v);
			}
		}
		namespace Segment_Tree
		{
			struct node
			{
				int minn, maxx, tag;
			}tree[N * 4];
			inline void update(const int rot)
			{
				tree[rot].minn = min(tree[rot << 1].minn, tree[rot << 1 | 1].minn);
				tree[rot].maxx = max(tree[rot << 1].maxx, tree[rot << 1 | 1].maxx);
			}
			inline void pushdown(const int rot)
			{
				int tag = tree[rot].tag;
				tree[rot << 1].minn = min(tree[rot << 1].minn, tag);
				tree[rot << 1].tag = min(tree[rot << 1].tag, tag);
				tree[rot << 1 | 1].minn = min(tree[rot << 1 | 1].minn, tag);
				tree[rot << 1 | 1].tag = min(tree[rot << 1 | 1].tag, tag);
				tree[rot].tag = INF;
			}
			void build(const int rot, const int lt, const int rt)
			{
				tree[rot].minn = tree[rot].tag = INF;
				if (lt == rt)
				{
					tree[rot].maxx = w[lt];
					return;
				}
				int mid = (lt + rt) >> 1;
				build(rot << 1, lt, mid);
				build(fot << 1 | 1, mid + 1, rt);
				update(rot);
			}
			void change_min(const int rot, const int lt, const int rt, const int ls, const int rs, const int w)
			{
				if (ls <= lt && rt <= rs)
				{
					tree[rot].minn = min(tree[rot].minn, w);
					tree[rot].tag = min(tree[rot].tag, w);
					return;
				}
				pushdown(rot);
				int mid = (lt + rt) >> 1;
				if (ls <= mid)
					change_min(rot << 1, lt, mid, ls, rs, w);
				if (rs > mid)
					change_min(rot << 1 | 1, mid + 1, rt, ls, rs, w);
				update(rot);
			}
			int query_max(const int rot, const int lt, const int rt, const int ls, const int rs)
			{
				if (ls <= lt && rt <= rs)
					return tree[rot].maxx;
				pushdown(rot);
				int mid = (lt + rt) >> 1, ans = 0;
				if (ls <= mid)
					ans = max(ans, query_max(rot << 1, lt, mid, ls, rs);
				if (rs > mid)
					ans = max(ans, query_max(rot << 1 | 1, mid + 1, rt, ls, rs);
				return ans;
			}
			int query_min(const int rot, const int lt, const int rt, const int pos)
			{
				if (lt == rt)
					return tree[rot].minn;
				pushdown(rot);
				int mid = (lt + rt) >> 1, ans = 0;
				if (pos <= mid)
					ans = max(ans, query_max(rot << 1, lt, mid, pos);
				else
					ans = max(ans, query_max(rot << 1 | 1, mid + 1, rt, pos);
				return ans;
			}
		}
		int query_max(int a, int b)
		{
			int ans = 0;
			while (top[a] != top[b])
			{
				if (dep[top[a]] < dep[top[b]])
					swap(a, b);
				ans = max(ans, Segment_Tree::query_max(1, 1, n, dfn[top[a]], dfn[a]));
				a = fa[top[a]];
			}
			if (a != b)
			{
				if (dep[a] < dep[b])
					swap(a, b);
				ans = max(ans, Segment_Tree::query_max(1, 1, n, dfn[b] + 1, dfn[a]));
			}
			return ans;
		}
		int query_min(const int a)
		{
			return query_min(1, 1, n, dfn[a]);
		}
		void change_min(int a, int b, const int w)
		{
			while (top[a] != top[b])
			{
				if (dep[top[a]] < dep[top[b]])
					swap(a, b);
				Segment_Tree::change_min(1, 1, n, dfn[top[a]], dfn[a], w);
				a = fa[top[a]];
			}
			if (a != b)
			{
				if (dep[a] < dep[b])
					swap(a, b);
				Segment_Tree::query_max(1, 1, n, dfn[b] + 1, dfn[a], w);
			}
		}
	}
	void Kruskal()
	{
		for (int i = 1; i <= n; i++)
			p[i] = i;
		for (int i = 0; i < m; i++)
		{
			int u = e[i].u, v = e[i].v, x = f(u), y = f(v);
			if (x != y)
			{
				p[x] = y;
				g[u].push_back((edge){v, e[i].w, e[i].id});
				g[v].push_back((edge){u, e[i].w, e[i].id});
				e[i].in_tree = true;
			}
		}
	}
	int work()
	{
		using namespace Tree_Chain_Cut;
		ios::sync_with_stdio(false);
		cin.tie(0);
		cin >> n >> m;
		memset(minn, INF, sizeof(int[n + 1][B]));
		for (int i = 0; i < m; i++)
		{
			cin >> e[i].u >> e[i].v >> e[i].w;
			e[i].id = i;
		}
		sort(e, e + m);
		Kruskal();
		dfs1(1, 0);
		dfs2(1, 1);
		Segment_Tree::build(1, 1, n);
		for (int i = 0; i < m; i++)
			if (!e[i].in_tree)
			{
				ans[e[i].id] = query_max(e[i].u, e[i].v) - 1;
				change_min(e[i].u, e[i].v, e[i].w);
			}
		}
		for (int i = 2; i <= n; i++)
			ans[pre[i]] = query_min(i);
		for (int i = 0; i < m; i++)
			if (ans[i] < INF - 1)
				cout << ans[i] << ' ';
			else
				cout << "-1 ";
		return 0;
	}
}
int main()
{
	return zyt::work();
}


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

namespace zyt
{
	const int N = 2e5 + 10, M = 2e5 + 10, B = 20, INF = 0x3f3f3f3f;
	int n, m;
	struct ed
	{
		int u, v, w, id;
		bool in_tree;
		bool operator < (const ed &b) const
		{
			return w < b.w;
		}
	}e[M];
	struct edge
	{
		int to, w, id;
	};
	vector<edge> g[N];
	int p[N], pre[N], pre_w[N], dep[N], w[N], son[N], size[N], dfn[N], top[N], fa[N], ans[N], cnt;
	int f(const int x)
	{
		return x == p[x] ? x : p[x] = f(p[x]);
	}
	namespace Tree_Chain_Cut
	{
		void dfs1(const int u, const int f)
		{
			dep[u] = dep[f] + 1;
			fa[u] = f;
			size[u] = 1;
			for (int i = 0; i < g[u].size(); i++)
			{
				int v = g[u][i].to;
				if (v == f)
					continue;
				pre[v] = g[u][i].id;
				pre_w[v] = g[u][i].w;
				dfs1(v, u);
				if (size[v] > size[son[u]])
					son[u] = v;
			}
		}
		void dfs2(const int u, const int t)
		{
			dfn[u] = ++cnt;
			w[dfn[u]] = pre_w[u];
			top[u] = t;
			if (son[u])
				dfs2(son[u], t);
			for (int i = 0; i < g[u].size(); i++)
			{
				int v = g[u][i].to;
				if (dfn[v])
					continue;
				dfs2(v, v);
			}
		}
		namespace Segment_Tree
		{
			struct node
			{
				int minn, maxx, tag;
			}tree[N * 4];
			inline void update(const int rot)
			{
				tree[rot].minn = min(tree[rot << 1].minn, tree[rot << 1 | 1].minn);
				tree[rot].maxx = max(tree[rot << 1].maxx, tree[rot << 1 | 1].maxx);
			}
			inline void pushdown(const int rot)
			{
				int tag = tree[rot].tag;
				tree[rot << 1].minn = min(tree[rot << 1].minn, tag);
				tree[rot << 1].tag = min(tree[rot << 1].tag, tag);
				tree[rot << 1 | 1].minn = min(tree[rot << 1 | 1].minn, tag);
				tree[rot << 1 | 1].tag = min(tree[rot << 1 | 1].tag, tag);
				tree[rot].tag = INF;
			}
			void build(const int rot, const int lt, const int rt)
			{
				tree[rot].minn = tree[rot].tag = INF;
				if (lt == rt)
				{
					tree[rot].maxx = w[lt];
					return;
				}
				int mid = (lt + rt) >> 1;
				build(rot << 1, lt, mid);
				build(rot << 1 | 1, mid + 1, rt);
				update(rot);
			}
			void change_min(const int rot, const int lt, const int rt, const int ls, const int rs, const int w)
			{
				if (ls <= lt && rt <= rs)
				{
					tree[rot].minn = min(tree[rot].minn, w);
					tree[rot].tag = min(tree[rot].tag, w);
					return;
				}
				pushdown(rot);
				int mid = (lt + rt) >> 1;
				if (ls <= mid)
					change_min(rot << 1, lt, mid, ls, rs, w);
				if (rs > mid)
					change_min(rot << 1 | 1, mid + 1, rt, ls, rs, w);
				update(rot);
			}
			int query_max(const int rot, const int lt, const int rt, const int ls, const int rs)
			{
				if (ls <= lt && rt <= rs)
					return tree[rot].maxx;
				pushdown(rot);
				int mid = (lt + rt) >> 1, ans = 0;
				if (ls <= mid)
					ans = max(ans, query_max(rot << 1, lt, mid, ls, rs));
				if (rs > mid)
					ans = max(ans, query_max(rot << 1 | 1, mid + 1, rt, ls, rs));
				return ans;
			}
			int query_min(const int rot, const int lt, const int rt, const int pos)
			{
				if (lt == rt)
					return tree[rot].minn;
				pushdown(rot);
				int mid = (lt + rt) >> 1, ans = 0;
				if (pos <= mid)
					return query_min(rot << 1, lt, mid, pos);
				else
					return query_min(rot << 1 | 1, mid + 1, rt, pos);
				return ans;
			}
		}
		int query_max_and_change_min(int a, int b, const int w)
		{
			int ans = 0;
			while (top[a] != top[b])
			{
				if (dep[top[a]] < dep[top[b]])
					swap(a, b);
				ans = max(ans, Segment_Tree::query_max(1, 1, n, dfn[top[a]], dfn[a]));
				Segment_Tree::change_min(1, 1, n, dfn[top[a]], dfn[a], w);
				a = fa[top[a]];
			}
			if (a != b)
			{
				if (dep[a] < dep[b])
					swap(a, b);
				ans = max(ans, Segment_Tree::query_max(1, 1, n, dfn[b] + 1, dfn[a]));
				Segment_Tree::change_min(1, 1, n, dfn[b] + 1, dfn[a], w);
			}
			return ans;
		}
		int query_min(const int a)
		{
			return Segment_Tree::query_min(1, 1, n, dfn[a]);
		}
	}
	void Kruskal()
	{
		for (int i = 1; i <= n; i++)
			p[i] = i;
		for (int i = 0; i < m; i++)
		{
			int u = e[i].u, v = e[i].v, x = f(u), y = f(v);
			if (x != y)
			{
				p[x] = y;
				g[u].push_back((edge){v, e[i].w, e[i].id});
				g[v].push_back((edge){u, e[i].w, e[i].id});
				e[i].in_tree = true;
			}
		}
	}
	int work()
	{
		using namespace Tree_Chain_Cut;
		ios::sync_with_stdio(false);
		cin.tie(0);
		cin >> n >> m;
		for (int i = 0; i < m; i++)
		{
			cin >> e[i].u >> e[i].v >> e[i].w;
			e[i].id = i;
		}
		sort(e, e + m);
		Kruskal();
		dfs1(1, 0);
		dfs2(1, 1);
		Segment_Tree::build(1, 1, n);
		for (int i = 0; i < m; i++)
			if (!e[i].in_tree)
				ans[e[i].id] = query_max_and_change_min(e[i].u, e[i].v, e[i].w) - 1;
		for (int i = 2; i <= n; i++)
			ans[pre[i]] = query_min(i) - 1;
		for (int i = 0; i < m; i++)
			if (ans[i] < INF - 1)
				cout << ans[i] << ' ';
			else
				cout << "-1 ";
		return 0;
	}
}
int main()
{
	return zyt::work();
}


//Andrew Yang
#include <iostream>
#include <stdio.h>
#include <sstream>
#include <fstream>
#include <string>
#include <string.h>
#include <vector>
#include <deque>
#include <queue>
#include <stack>
#include <set>
#include <unordered_set>
#include <map>
#include <unordered_map>
#include <algorithm>
#include <functional>
#include <utility>
#include <bitset>
#include <cmath>
#include <cstdlib>
#include <ctime>
#include <cstdio>
#include <climits>
using namespace std;
#define FOR(index, start, end) for(int index = start; index < end; index++)
#define RFOR(index, start, end) for(int index = start; index > end; index--)
#define FOREACH(itr, b) for(auto itr = b.begin(); itr != b.end(); itr++)
#define RFOREACH(itr, b) for(auto itr = b.rbegin(); itr != b.rend(); itr++)
#define INF 1000000000
#define M 1000000007
typedef long long ll;
typedef pair<int, int> pii;
int x[200001];
int dis[200001];
int main()
{
	int n, m, s, d;
	scanf("%d%d%d%d", &n, &m, &s, &d);
	FOR(i, 0, n)
	{
		scanf("%d", &x[i]);
	}
	sort(x, x + n);
	dis[0] = x[0] - 1;
	FOR(i, 1, n)
	{
		dis[i] = x[i] - x[i - 1] - 2;
	}
	vector<pair<string, int>> ans;
	FOR(i, 0, n)
	{
		if (dis[i] < s)
		{
			cout << "IMPOSSIBLE" << endl;
			return 0;
		}
		ans.push_back({ "RUN", dis[i] });
		int jump = 1;
		FOR(j, i + 1, n)
		{
			if (dis[j] >= s)
			{
				i = j - 1;
				break;
			}
			else
			{
				jump += dis[j] + 1;
			}
		}
		jump++;
		if (jump > d)
		{
			cout << "IMPOSSIBLE" << endl;
			return 0;
		}
		ans.push_back({ "JUMP", jump });
	}
	if (m - x[n - 1] - 1 > 0)
	{
		ans.push_back({ "RUN", m - x[n - 1] - 1 });
	}
	FOR(i, 0, ans.size())
	{
		cout << ans[i].first << " " << ans[i].second << endl;
	}
}


//Andrew Yang
#include <iostream>
#include <stdio.h>
#include <sstream>
#include <fstream>
#include <string>
#include <string.h>
#include <vector>
#include <deque>
#include <queue>
#include <stack>
#include <set>
#include <unordered_set>
#include <map>
#include <unordered_map>
#include <algorithm>
#include <functional>
#include <utility>
#include <bitset>
#include <cmath>
#include <cstdlib>
#include <ctime>
#include <cstdio>
#include <climits>
using namespace std;
#define FOR(index, start, end) for(int index = start; index < end; index++)
#define RFOR(index, start, end) for(int index = start; index > end; index--)
#define FOREACH(itr, b) for(auto itr = b.begin(); itr != b.end(); itr++)
#define RFOREACH(itr, b) for(auto itr = b.rbegin(); itr != b.rend(); itr++)
#define INF 1000000000
#define M 1000000007
typedef long long ll;
typedef pair<int, int> pii;
int x[200001];
int dis[200001];
int main()
{
	int n, m, s, d;
	scanf("%d%d%d%d", &n, &m, &s, &d);
	FOR(i, 0, n)
	{
		scanf("%d", &x[i]);
	}
	sort(x, x + n);
	dis[0] = x[0] - 1;
	FOR(i, 1, n)
	{
		dis[i] = x[i] - x[i - 1] - 2;
	}
	vector<pair<string, int>> ans;
	FOR(i, 0, n)
	{
		if (dis[i] < s)
		{
			cout << "IMPOSSIBLE" << endl;
			return 0;
		}
		ans.push_back({ "RUN", dis[i] });
		int jump = 1;
		FOR(j, i + 1, n)
		{
			if (dis[j] >= s)
			{
				i = j - 1;
				break;
			}
			else
			{
				jump += dis[j] + 2;
			}
		}
		jump++;
		if (jump > d)
		{
			cout << "IMPOSSIBLE" << endl;
			return 0;
		}
		ans.push_back({ "JUMP", jump });
	}
	if (m - x[n - 1] - 1 > 0)
	{
		ans.push_back({ "RUN", m - x[n - 1] - 1 });
	}
	FOR(i, 0, ans.size())
	{
		cout << ans[i].first << " " << ans[i].second << endl;
	}
}


//Andrew Yang
#include <iostream>
#include <stdio.h>
#include <sstream>
#include <fstream>
#include <string>
#include <string.h>
#include <vector>
#include <deque>
#include <queue>
#include <stack>
#include <set>
#include <unordered_set>
#include <map>
#include <unordered_map>
#include <algorithm>
#include <functional>
#include <utility>
#include <bitset>
#include <cmath>
#include <cstdlib>
#include <ctime>
#include <cstdio>
#include <climits>
using namespace std;
#define FOR(index, start, end) for(int index = start; index < end; index++)
#define RFOR(index, start, end) for(int index = start; index > end; index--)
#define FOREACH(itr, b) for(auto itr = b.begin(); itr != b.end(); itr++)
#define RFOREACH(itr, b) for(auto itr = b.rbegin(); itr != b.rend(); itr++)
#define INF 1000000000
#define M 1000000007
typedef long long ll;
typedef pair<int, int> pii;
int x[200001];
int dis[200001];
int main()
{
	int n, m, s, d;
	scanf("%d%d%d%d", &n, &m, &s, &d);
	FOR(i, 0, n)
	{
		scanf("%d", &x[i]);
	}
	sort(x, x + n);
	dis[0] = x[0] - 1;
	FOR(i, 1, n)
	{
		dis[i] = x[i] - x[i - 1] - 2;
	}
	vector<pair<string, int>> ans;
	FOR(i, 0, n)
	{
		if (dis[i] < s)
		{
			cout << "IMPOSSIBLE" << endl;
			return 0;
		}
		ans.push_back({ "RUN", dis[i] });
		int jump = 1;
		FOR(j, i + 1, n + 1)
		{
			if (dis[j] >= s || j == n)
			{
				i = j - 1;
				break;
			}
			else
			{
				jump += dis[j] + 2;
			}
		}
		jump++;
		if (jump > d)
		{
			cout << "IMPOSSIBLE" << endl;
			return 0;
		}
		ans.push_back({ "JUMP", jump });
	}
	if (m - x[n - 1] - 1 > 0)
	{
		ans.push_back({ "RUN", m - x[n - 1] - 1 });
	}
	FOR(i, 0, ans.size())
	{
		cout << ans[i].first << " " << ans[i].second << endl;
	}
}


#include <iostream>
#include <cmath>
#include <cstdio>
#include <algorithm>
#include <string>
#include <ctime>
#include <cstdlib>
#include <vector>
#include <map>

using namespace std;

int main()
{
	int mas[200000];
	int n, m, s, d;
	int i, j, k, l, pos;

	cin >> n >> m >> s >> d;

	for (i = 0; i < n; i++)
		cin >> mas[i];

	sort(mas, mas + n);

	pos = 0;
	k = 0;
	vector<pair<int, int>> v;
	while (k < n)
	{

		if (mas[k] - pos < s)
		{
			cout << "IMPOSSIBLE";
			return 0;
		}

		v.push_back(make_pair(0, mas[k] - pos - 1));
		pos = mas[k] - 1;

		i = k;
		while (i < n - 1 && mas[i + 1] - mas[i] - 1 < s) i++;

		if (mas[i] - pos + 1 > d)
		{
			cout << "IMPOSSIBLE";
			return 0;
		}

		v.push_back(make_pair(1, mas[i] - pos + 1));
		pos = mas[i] + 1;
		k = i + 1;

	}

	v.push_back(make_pair(0, m - pos));

	for (i = 0; i < v.size(); i++)
	{
		if (v[i].first == 0)
			cout << "RUN ";
		else
			cout << "JUMP ";
		cout << v[i].second << endl;
	}
}


#include <iostream>
#include <cmath>
#include <cstdio>
#include <algorithm>
#include <string>
#include <ctime>
#include <cstdlib>
#include <vector>
#include <map>

using namespace std;

int main()
{
	int mas[200000];
	int n, m, s, d;
	int i, j, k, l, pos;

	cin >> n >> m >> s >> d;

	for (i = 0; i < n; i++)
		cin >> mas[i];

	sort(mas, mas + n);

	pos = 0;
	k = 0;
	vector<pair<int, int>> v;
	while (k < n)
	{

		if (mas[k] - pos - 1 < s)
		{
			cout << "IMPOSSIBLE";
			return 0;
		}

		v.push_back(make_pair(0, mas[k] - pos - 1));
		pos = mas[k] - 1;

		i = k;
		while (i < n - 1 && mas[i + 1] - mas[i] - 2 < s) i++;

		if (mas[i] - pos + 1 > d)
		{
			cout << "IMPOSSIBLE";
			return 0;
		}

		v.push_back(make_pair(1, mas[i] - pos + 1));
		pos = mas[i] + 1;
		k = i + 1;

	}

	v.push_back(make_pair(0, m - pos));

	for (i = 0; i < v.size(); i++)
	{
		if (v[i].second == 0)
			continue;
		if (v[i].first == 0)
			cout << "RUN ";
		else
			cout << "JUMP ";
		cout << v[i].second << endl;
	}
}


#include <iostream>
#include <cmath>
#include <cstdio>
#include <algorithm>
#include <string>
#include <ctime>
#include <cstdlib>
#include <vector>
#include <map>

using namespace std;

int main()
{
	int mas[200000];
	int n, m, s, d;
	int i, j, k, l, pos;

	cin >> n >> m >> s >> d;

	for (i = 0; i < n; i++)
		cin >> mas[i];

	sort(mas, mas + n);

	pos = 0;
	k = 0;
	vector<pair<int, int>> v;
	while (k < n)
	{

		if (mas[k] - pos - 1 < s)
		{
			cout << "IMPOSSIBLE";
			return 0;
		}

		v.push_back(make_pair(0, mas[k] - pos - 1));
		pos = mas[k] - 1;

		i = k;
		while (i < n - 1 && mas[i + 1] - mas[i] - 1 < s) i++;

		if (mas[i] - pos + 1 > d)
		{
			cout << "IMPOSSIBLE";
			return 0;
		}

		v.push_back(make_pair(1, mas[i] - pos + 1));
		pos = mas[i] + 1;
		k = i + 1;

	}

	v.push_back(make_pair(0, m - pos));

	for (i = 0; i < v.size(); i++)
	{
		if (v[i].second == 0)
			continue;
		if (v[i].first == 0)
			cout << "RUN ";
		else
			cout << "JUMP ";
		cout << v[i].second << endl;
	}
}


#include <iostream>
#include <cmath>
#include <cstdio>
#include <algorithm>
#include <string>
#include <ctime>
#include <cstdlib>
#include <vector>
#include <map>

using namespace std;

int main()
{
	int mas[200000];
	int n, m, s, d;
	int i, j, k, l, pos;

	cin >> n >> m >> s >> d;

	for (i = 0; i < n; i++)
		cin >> mas[i];

	sort(mas, mas + n);

	pos = 0;
	k = 0;
	vector<pair<int, int>> v;
	while (k < n)
	{

		if (mas[k] - pos - 1 < s)
		{
			cout << "IMPOSSIBLE";
			return 0;
		}

		v.push_back(make_pair(0, mas[k] - pos - 1));
		pos = mas[k] - 1;

		i = k;
		while (i < n - 1 && mas[i + 1] - mas[i] - 1 < s) i++;

		if (mas[i] - pos + 1 > d)
		{
			cout << "IMPOSSIBLE";
			return 0;
		}

		v.push_back(make_pair(1, mas[i] - pos + 1));
		pos = mas[i] + 1;
		k = i + 1;

	}

	v.push_back(make_pair(0, m - pos));

	for (i = 0; i < v.size(); i++)
	{
		if (v[i].first == 0)
			cout << "RUN ";
		else
			cout << "JUMP ";
		cout << v[i].second << endl;
	}
}


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

typedef pair<int, int> PII;

int main() {
	int n, m, s, d;
	cin >> n >> m >> s >> d;
	vector<int> trap(n + 2);
	for (int k = 0; k < n; k++) {
		cin >> trap[k];
	}
	trap[n] = -1;
	trap[n + 1] = m + 1;
	sort(trap.begin(), trap.end());

	vector<PII> list;
	for (int k = 0; k < n + 1; k++) {
		int left = trap[k] + 1, right = trap[k + 1] - 1;
		if (k != n && right - left < s && left != 0) {
			continue;
		}
		list.push_back(PII(left, right));
		if (list.size() > 1) {
			if (list[list.size() - 1].first - list[list.size() - 2].second > d) {
				cout << "IMPOSSIBLE";
				return 0;
			}
		}
	}
	for (int k = 0; k < (int)list.size(); k++) {
		if (list[k].second != list[k].first) {
			cout << "RUN " << list[k].second - list[k].first << '\n';
		}
		if (k != (int)list.size() - 1) {
			cout << "JUMP " << list[k + 1].first - list[k].second << '\n';
		}
	}
	return 0;
}


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

typedef pair<int, int> PII;

int main() {
	ios_base::sync_with_stdio(false);
	int n, m, s, d;
	cin >> n >> m >> s >> d;
	vector<int> trap(n + 2);
	for (int k = 0; k < n; k++) {
		cin >> trap[k];
	}
	trap[n] = -1;
	trap[n + 1] = m + 1;
	sort(trap.begin(), trap.end());

	vector<PII> list;
	for (int k = 0; k < n + 1; k++) {
		int left = trap[k] + 1, right = trap[k + 1] - 1;
		if (k != n && right - left < s) {
			if (left == 0) {
				cout << "IMPOSSIBLE";
				return 0;
			}
			continue;
		}
		list.push_back(PII(left, right));
		if (list.size() > 1) {
			if (list[list.size() - 1].first - list[list.size() - 2].second > d) {
				cout << "IMPOSSIBLE";
				return 0;
			}
		}
	}
	for (int k = 0; k < (int)list.size(); k++) {
		if (list[k].second != list[k].first) {
			cout << "RUN " << list[k].second - list[k].first << '\n';
		}
		if (k != (int)list.size() - 1) {
			cout << "JUMP " << list[k + 1].first - list[k].second << '\n';
		}
	}
	return 0;
}


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

typedef pair<int, int> PII;

int main() {
    ios_base::sync_with_stdio(false);
	int n, m, s, d;
	cin >> n >> m >> s >> d;
	vector<int> trap(n + 2);
	for (int k = 0; k < n; k++) {
		cin >> trap[k];
	}
	trap[n] = -1;
	trap[n + 1] = m + 1;
	sort(trap.begin(), trap.end());

	vector<PII> list;
	for (int k = 0; k < n + 1; k++) {
		int left = trap[k] + 1, right = trap[k + 1] - 1;
		if (k != n && right - left < s) {
			if (left == 0 || right == n) {
				cout << "IMPOSSIBLE";
				return 0;
			}
			continue;
		}
		list.push_back(PII(left, right));
		if (list.size() > 1) {
			if (list[list.size() - 1].first - list[list.size() - 2].second > d) {
				cout << "IMPOSSIBLE";
				return 0;
			}
		}
	}
	for (int k = 0; k < (int)list.size(); k++) {
		if (list[k].second != list[k].first) {
			cout << "RUN " << list[k].second - list[k].first << '\n';
		}
		if (k != (int)list.size() - 1) {
			cout << "JUMP " << list[k + 1].first - list[k].second << '\n';
		}
	}
	return 0;
}


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

typedef pair<int, int> PII;

int main() {
	int n, m, s, d;
	cin >> n >> m >> s >> d;
	vector<int> trap(n + 2);
	for (int k = 0; k < n; k++) {
		cin >> trap[k];
	}
	trap[n] = -1;
	trap[n + 1] = m + 1;
	sort(trap.begin(), trap.end());

	vector<PII> list;
	for (int k = 0; k < n + 1; k++) {
		int left = trap[k] + 1, right = trap[k + 1] - 1;
		if (k != n && right - left < s) {
			continue;
		}
		list.push_back(PII(left, right));
		if (list.size() > 1) {
			if (list[list.size() - 1].first - list[list.size() - 2].second > d) {
				cout << "IMPOSSIBLE";
				return 0;
			}
		}
	}
	for (int k = 0; k < (int)list.size(); k++) {
		if (list[k].second != list[k].first) {
			cout << "RUN " << list[k].second - list[k].first << '\n';
		}
		if (k != (int)list.size() - 1) {
			cout << "JUMP " << list[k + 1].first - list[k].second << '\n';
		}
	}
	return 0;
}


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

typedef pair<int, int> PII;

int main() {
	int n, m, s, d;
	cin >> n >> m >> s >> d;
	vector<int> trap(n + 2);
	for (int k = 0; k < n; k++) {
		cin >> trap[k];
	}
	trap[n] = -1;
	trap[n + 1] = m + 1;
	sort(trap.begin(), trap.end());

	vector<PII> list;
	bool f = true;
	for (int k = 0; k < n + 1; k++) {
		int left = trap[k] + 1, right = trap[k + 1] - 1;
		if (k != n && right - left < s) {
			continue;
		}
		f = false;
		list.push_back(PII(left, right));
		if (list.size() > 1) {
			if (list[list.size() - 1].first - list[list.size() - 2].second > d) {
				cout << "IMPOSSIBLE";
				return 0;
			}
		}
	}
	if (f) {
		cout << "IMPOSSIBLE";
		return 0;
	}
	f = true;
	for (int k = 0; k < (int)list.size(); k++) {
		if (list[k].second != list[k].first) {
			cout << "RUN " << list[k].second - list[k].first << '\n';
			f = false;
		}
		if (k != (int)list.size() - 1) {
			cout << "JUMP " << list[k + 1].first - list[k].second << '\n';
			f = false;
		}
	}
	if (f) {
		cout << "IMPOSSIBLE";
		return 0;
	}
	return 0;
}


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

typedef pair<int, int> PII;

int main() {
	int n, m, s, d;
	cin >> n >> m >> s >> d;
	vector<int> trap(n + 2);
	for (int k = 0; k < n; k++) {
		cin >> trap[k];
	}
	trap[n] = -1;
	trap[n + 1] = m + 1;
	sort(trap.begin(), trap.end());

	vector<PII> list;
	for (int k = 0; k < n + 1; k++) {
		int left = trap[k] + 1, right = trap[k + 1] - 1;
		if (right - left < s) {
			continue;
		}
		list.push_back(PII(left, right));
		if (list.size() > 1) {
			if (list[list.size() - 1].first - list[list.size() - 2].second > d) {
				cout << "IMPOSSIBLE";
				return 0;
			}
		}
	}
	for (int k = 0; k < (int)list.size(); k++) {
		cout << "RUN " << list[k].second - list[k].first << '\n';
		if (k != (int)list.size() - 1) {
			cout << "JUMP " << list[k + 1].first - list[k].second << '\n';
		}
	}
	return 0;
}


#include<bits/stdc++.h>
using namespace std;

const int N = 2e5 + 6;
int n, m, s, d;
int a[N];
vector< pair<int, int> > segs;
vector<string> ans;

int main()
{
	cin >> n >> m >> s >> d;
	for(int i = 1; i <= n; i++)
	{
		cin >> a[i];
	}

	sort(a + 1, a + 1 + n);
	a[0] = 0;
	a[n + 1] = m;
	int fl = 0;
	int curPos = 0;

	for(int i = 1; i <= n + 1; i++)
	{
		int rightFree = a[i] - 1;
		int leftFree = a[i - 1] + 1;
		if(i == n + 1)rightFree = m;
		//cout << i << " " << leftFree << " hehehe " << rightFree << endl;
		if(rightFree < leftFree)continue;

		//cout << "here " << leftFree << " " << rightFree << endl;;
		if(i == 1 and (rightFree - leftFree + 1 < s))continue;
		if((i != n + 1 and i != 1) and rightFree - leftFree < s)continue;
		if(i != 1 and i != (n + 1))
		segs.push_back(make_pair(leftFree, rightFree));

		else if(i == 1)
		{
			//cout << "here " << leftFree << " " << rightFree << endl;;
			segs.push_back(make_pair(0, rightFree));
		}
		else if(i == n + 1)
		{
			segs.push_back(make_pair(leftFree, m));
		}
		//cout << "zza " << i << endl;
	}
	//cout << "dsadsa " << segs.size() << endl;
	for(int i = 1; i < segs.size() - 1; i++)
	{
		if(segs[i].first - segs[i - 1].second > d)
		{
			cout << "IMPOSSIBLE";
			return 0;
		}
	}

	for(int i = 0; i < segs.size(); i++)
	{
		//cout << segs[i].first << " " << segs[i].second << endl;
	}
	//int curPos = 0;
	for(int i = 0; i < segs.size(); i++)
	{
		if(i != (segs.size() - 1))
		{
			fl = 1;
			cout << "RUN ";
			cout << segs[i].second - segs[i].first << endl;
			cout << "JUMP ";
			cout << segs[i + 1].first - segs[i].second << endl;
			//curPos = segs[i + 1].first;
			if(segs[i + 1].first == m)break;
		}
		else
		{
			fl = 1;
			cout << "RUN ";
			cout << segs[i].second - segs[i].first << endl;
		}
	}
	if(!fl)
	{
		cout << "IMPOSSIBLE";
		return 0;
	}
}


#include<bits/stdc++.h>
using namespace std;

const int N = 2e5 + 6;
int n, m, s, d;
int a[N];
vector< pair<int, int> > segs;
vector<string> ans;

int main()
{
	cin >> n >> m >> s >> d;
	for(int i = 1; i <= n; i++)
	{
		cin >> a[i];
	}

	sort(a + 1, a + 1 + n);
	a[0] = 0;
	a[n + 1] = m;
	int fl = 0;
	int curPos = 0;

	for(int i = 1; i <= n + 1; i++)
	{
		int rightFree = a[i] - 1;
		int leftFree = a[i - 1] + 1;
		if(rightFree < leftFree)continue;
		if((i != n + 1) and rightFree - leftFree < s)continue;
		if(i != 1 and i != (n + 1))
		segs.push_back(make_pair(leftFree, rightFree));
		else if(i == 1)
		{
			segs.push_back(make_pair(0, rightFree));
		}
		else if(i == n + 1)
		{
			segs.push_back(make_pair(leftFree, m));
		}
	}

	for(int i = 1; i < segs.size(); i++)
	{
		if(segs[i].first - segs[i - 1].second > d)
		{
			cout << "IMPOSSIBLE";
			return 0;
		}
	}

	for(int i = 0; i < segs.size(); i++)
	{
		//cout << segs[i].first << " " << segs[i].second << endl;
	}

	for(int i = 0; i < segs.size(); i++)
	{
		if(i != (segs.size() - 1))
		{
			fl = 1;
			cout << "RUN ";
			cout << segs[i].second - segs[i].first << endl;
			cout << "JUMP ";
			cout << segs[i + 1].first - segs[i].second << endl;
		}
		else
		{
			fl = 1;
			cout << "RUN ";
			cout << segs[i].second - segs[i].first << endl;
		}
	}
	if(!fl)
	{
		cout << "IMPOSSIBLE";
		return 0;
	}
}


#include<bits/stdc++.h>
using namespace std;

const int N = 2e5 + 6;
int n, m, s, d;
int a[N];
vector< pair<int, int> > segs;
vector<string> ans;

int main()
{
	cin >> n >> m >> s >> d;
	for(int i = 1; i <= n; i++)
	{
		cin >> a[i];
	}

	sort(a + 1, a + 1 + n);
	a[0] = 0;
	a[n + 1] = m;
	int curPos = 0;

	for(int i = 1; i <= n + 1; i++)
	{
		int rightFree = a[i] - 1;
		int leftFree = a[i - 1] + 1;
		if(i == 1)
		{
			segs.push_back(make_pair(0, rightFree));
		}
		else if(i == n + 1)
		{
			segs.push_back(make_pair(leftFree, m));
		}
		else
		{
			if(leftFree > rightFree)continue;
			if(rightFree - leftFree < s)continue;
			segs.push_back(make_pair(leftFree, rightFree));
		}
	}

	int fl = 0;
	for(int i = 0; i < segs.size() - 1;  i++)
	{
		if(segs[i].second - segs[i].first < s)fl = 1;
	}
 	for(int i = 1; i < segs.size(); i++)
	{
		if(segs[i].first - segs[i - 1].second > d)fl = 1;
	}

	if(fl)
	{
		cout << "IMPOSSIBLE";
		return 0;
	}

	for(int i = 0; i < segs.size(); i++)
	{
		//cout << segs[i].first << " " << segs[i].second << endl;
	}

	for(int i = 0; i < segs.size(); i++)
	{
		if(i != segs.size() - 1)
		{
			cout << "RUN ";
			cout << segs[i].second - segs[i].first << endl;
			cout << "JUMP ";
			cout << segs[i + 1].first - segs[i].second << endl;
			if(segs[i + 1].first == m)break;
		}
		else
		{
			cout << "RUN ";
			cout << segs[i].second - segs[i].first << endl;
		}
	}
}


#include<bits/stdc++.h>
using namespace std;

const int N = 2e5 + 6;
int n, m, s, d;
int a[N];
vector< pair<int, int> > segs;
vector<string> ans;

int main()
{
	cin >> n >> m >> s >> d;
	for(int i = 1; i <= n; i++)
	{
		cin >> a[i];
	}

	sort(a + 1, a + 1 + n);
	a[0] = 0;
	a[n + 1] = m;
	int curPos = 0;

	for(int i = 1; i <= n + 1; i++)
	{
		int rightFree = a[i] - 1;
		int leftFree = a[i - 1] + 1;
		if(rightFree < leftFree)continue;
		if(rightFree - leftFree + 1 < s)continue;
		if(i != 1 and i != (n + 1))
		segs.push_back(make_pair(leftFree, rightFree));
		else if(i == 1)
		{
			segs.push_back(make_pair(0, rightFree));
		}
		else if(i == n + 1)
		{
			segs.push_back(make_pair(leftFree, m));
		}
	}

	for(int i = 1; i < segs.size(); i++)
	{
		if(segs[i].first - segs[i - 1].second > d)
		{
			cout << "IMPOSSIBLE";
			return 0;
		}
	}

	for(int i = 0; i < segs.size(); i++)
	{
		//cout << segs[i].first << " " << segs[i].second << endl;
	}

	for(int i = 0; i < segs.size(); i++)
	{
		if(i != (segs.size() - 1))
		{
			cout << "RUN ";
			cout << segs[i].second - segs[i].first << endl;
			cout << "JUMP ";
			cout << segs[i + 1].first - segs[i].second << endl;
		}
		else
		{
			cout << "RUN ";
			cout << segs[i].second - segs[i].first << endl;
		}
	}
}