Language: C++

#include <bits/stdc++.h>

using namespace std;

#define int long long

#define rep(i,x) for(int i=0;i<x;++i)
#define rrep(i,x) for(int i=x-1;i>=0;--i)
#define rep1(i,x) for(int i=1;i<=x;++i)
#define PB push_back
#define PPB pop_back
#define fst first
#define scd second

using vi = vector<int>;
using vvi = vector<vi>;
using pii = pair<int, int>;
using vpii = vector<pii>;

struct edge {int to, cost;};
using Graph = vector<edge>;

const int inf = 3e18;

struct UF {
    vi data;
    UF(int n) {
        data.resize(n, -1);
    }
    int root(int i) {
        return data[i] < 0 ? i : data[i] = root(data[i]);
    }
    int size(int x) {
        x = root(x);
        return -data[x];
    }
    void unite(int x, int y) {
        x = root(x), y = root(y);
        if (x == y) return;
        if (size(x) < size(y)) swap(x, y);
        data[x] += data[y];
        data[y] = x;
    }
    bool same(int x, int y) {
        x = root(x), y = root(y);
        return x == y;
    }
};

Graph G[100010];
int d[100010];
int N, M, K, Q;
int F[100010];

// LCA??¨
constexpr int max_log_n = log2(100010);
vi tr[100010];
int parent[100010][max_log_n + 5];
int minimum[100010][max_log_n + 5];
int depth[100010];

void lca_dfs(int cur = 0, int par = -1, int dep = 0)
{
    parent[cur][0] = par;
    minimum[cur][0] = min(d[cur], par == -1 ? inf : d[par]);
    depth[cur] = dep;

    for (int nx : tr[cur]) {
        if (nx == par) continue;
        lca_dfs(nx, cur, dep + 1);
    }
}

void lca_init()
{
    lca_dfs();

    rep(i, max_log_n) {
        rep(j, N) {
            if (~parent[j][i]) {
                parent[j][i + 1] = parent[parent[j][i]][i];
                minimum[j][i + 1] = min(minimum[j][i], minimum[parent[j][i]][i]);
            } else {
                parent[j][i + 1] = -1;
                minimum[j][i + 1] = inf;
            }
        }
    }
}

int lca(int u, int v)
{
    if (depth[u] > depth[v]) swap(u, v);

    int diff = depth[v] - depth[u];

    rep(i, max_log_n + 1) {
        if (diff >> i & 1) v = parent[v][i];
    }

    if (u == v) return u;

    rrep(i, max_log_n + 1) {
        if (parent[u][i] != parent[v][i]) {
            u = parent[u][i];
            v = parent[v][i];
        }
    }

    return parent[u][0];
}

int calc2(int p, int c)
{
    if (p == c) return d[p];

    int dif = depth[c] - depth[p];

    int mi = d[c];

    rep(i, max_log_n+1) {
        if (dif & 1 << i) {
            mi = min(mi, minimum[c][i]);
            c = parent[c][i];
        }
    }

    return mi;
}

int calc(int u, int v)
{
    if (u == v) return d[u];

    int l = lca(u, v);

    u = calc2(l, u), v = calc2(l, v);

    return min(u, v);
}

void dijkstra()
{
    priority_queue<pii, vpii, greater<pii>> q;
    rep(i, K) {
        d[F[i]] = 0;
        q.push(pii(0, F[i]));
    }
    while (q.size()) {
        pii p = q.top(); q.pop();
        int v = p.scd;
        if (d[v] < p.fst) continue;
        for (edge &e : G[v]) {
            if (d[e.to] > d[v] + e.cost) {
                d[e.to] = d[v] + e.cost;
                q.push(pii(d[e.to], e.to));
            }
        }
    }
}

void build_tree()
{
    using EdgeInfo = pair<int, pair<int, int>>;
    vector<EdgeInfo> E;

    rep(i, N) {
        for (edge& e : G[i]) {
            E.PB(EdgeInfo{pii(d[i], d[e.to]), pii(i, e.to)});
        }
    }

    sort(begin(E), end(E), greater<EdgeInfo>());

    UF uf(N);

    int n = E.size();
    rep(i, n) {
        int from = E[i].scd.fst, to = E[i].scd.scd;
        
        if (uf.same(from, to)) continue;
        uf.unite(from, to);

        tr[from].PB(to);
        tr[to].PB(from);
    }
}

signed main()
{
    cin >> N >> M >> K >> Q;

    rep(i, M) {
        int a, b, l; cin >> a >> b >> l;
        --a, --b;

        G[a].PB(edge{b, l});
        G[b].PB(edge{a, l});
    }

    rep(i, K) {
        cin >> F[i];
        --F[i];
    }

    fill_n(d, N + 1, inf);
    dijkstra();

    build_tree();

    lca_init();

    rep(i, Q) {
        int s, t; cin >> s >> t;
        --s, --t;
        int v = calc(s, t);
        cout << v << endl;
    }

    //rep(i, N) {
    //    cout << "d[" << i+1 << "] = " << d[i] << endl;
    //}

    //cout << "tree_debug:\n";
    //rep(v, N) {
    //    for (int u : tr[v]) {
    //        if (v < u) {
    //            cout << v+1 << " <-> " << u+1 << endl;
    //        }
    //    }
    //}
}

Compiler output:
a.cc: In function 'void build_tree()':
a.cc:169:59: error: no matching function for call to 'std::pair<long long int, std::pair<long long int, long long int> >::pair(<brace-enclosed initializer list>)'
  169 |             E.PB(EdgeInfo{pii(d[i], d[e.to]), pii(i, e.to)});
      |                                                           ^
In file included from /usr/include/c++/14/bits/stl_algobase.h:64,
                 from /usr/include/c++/14/algorithm:60,
                 from /usr/include/x86_64-linux-gnu/c++/14/bits/stdc++.h:51,
                 from a.cc:1:
/usr/include/c++/14/bits/stl_pair.h:913:28: note: candidate: 'template<class _U1, class _U2, typename std::enable_if<(std::_PCC<((! std::is_same<long long int, _U1>::value) || (! std::is_same<std::pair<long long int, long long int>, _U2>::value)), long long int, std::pair<long long int, long long int> >::_MoveConstructiblePair<_U1, _U2>() && (! std::_PCC<((! std::is_same<long long int, _U1>::value) || (! std::is_same<std::pair<long long int, long long int>, _U2>::value)), long long int, std::pair<long long int, long long int> >::_ImplicitlyMoveConvertiblePair<_U1, _U2>())), bool>::type <anonymous> > constexpr std::pair<_T1, _T2>::pair(std::pair<_U1, _U2>&&) [with _U2 = _U1; typename std::enable_if<(std::_PCC<((! std::is_same<_T1, _U1>::value) || (! std::is_same<_T2, _U2>::value)), _T1, _T2>::_MoveConstructiblePair<_U1, _U2>() && (! std::_PCC<((! std::is_same<_T1, _U1>::value) || (! std::is_same<_T2, _U2>::value)), _T1, _T2>::_ImplicitlyMoveConvertiblePair<_U1, _U2>())), bool>::type <anonymous> = _U2; _T1 = long long int; _T2 = std::pair<long long int, long long int>]'
  913 |         explicit constexpr pair(pair<_U1, _U2>&& __p)
      |                            ^~~~
/usr/include/c++/14/bits/stl_pair.h:913:28: note:   candidate expects 1 argument, 2 provided
/usr/include/c++/14/bits/stl_pair.h:902:19: note: candidate: 'template<class _U1, class _U2, typename std::enable_if<(std::_PCC<((! std::is_same<long long int, _U1>::value) || (! std::is_same<std::pair<long long int, long long int>, _U2>::value)), long long int, std::pair<long long int, long long int> >::_MoveConstructiblePair<_U1, _U2>() && std::_PCC<((! std::is_same<long long int, _U1>::value) || (! std::is_same<std::pair<long long int, long long int>, _U2>::value)), long long int, std::pair<long long int, long long int> >::_ImplicitlyMoveConvertiblePair<_U1, _U2>()), bool>::type <anonymous> > constexpr std::pair<_T1, _T2>::pair(std::pair<_U1, _U2>&&) [with _U2 = _U1; typename std::enable_if<(std::_PCC<((! std::is_same<_T1, _U1>::value) || (! std::is_same<_T2, _U2>::value)), _T1, _T2>::_MoveConstructiblePair<_U1, _U2>() && std::_PCC<((! std::is_same<_T1, _U1>::value) || (! std::is_same<_T2, _U2>::value)), _T1, _T2>::_ImplicitlyMoveConvertiblePair<_U1, _U2>()), bool>::type <anonymous> = _U2; _T1 = long long int; _T2 = std::pair<long long int, long long int>]'
  902 |         constexpr pair(pair<_U1, _U2>&& __p)
      |                   ^~~~
/usr/include/c++/14/bits/stl_pair.h:902:19: note:   candidate expects 1 argument, 2 provided
/usr/include/c++/14/bits/stl_pair.h:891:28: note: candidate: 'template<class _U1, class _U2, typename std::enable_if<(_MoveConstructiblePair<_U1, _U2>() && (! _ImplicitlyMoveConvertiblePair<_U1, _U2>())), bool>::type <anonymous> > constexpr std::pair<_T1, _T2>::pair(_U1&&, _U2&&) [with _U2 = _U1; typename std::enable_if<(std::_PCC<true, _T1, _T2>::_MoveConstructiblePair<_U1, _U2>() && (! std::_PCC<true, _T1, _T2>::_ImplicitlyMoveConvertiblePair<_U1, _U2>())), bool>::type <anonymous> = _U2; _T1 = long long int; _T2 = std::pair<long long int, long long int>]'
  891 |         explicit constexpr pair(_U1&& __x, _U2&& __y)
      |                            ^~~~
/usr/include/c++/14/bits/stl_pair.h:891:28: note:   template argument deduction/substitution failed:
/usr/include/c++/14/bits/stl_pair.h:890:38: error: no type named 'type' in 'struct std::enable_if<false, bool>'
  890 |                          bool>::type=false>
      |                                      ^~~~~
/usr/include/c++/14/bits/stl_pair.h:881:19: note: candidate: 'template<class _U1, class _U2, typename std::enable_if<(_MoveConstructiblePair<_U1, _U2>() && _ImplicitlyMoveConvertiblePair<_U1, _U2>()), bool>::type <anonymous> > constexpr std::pair<_T1, _T2>::pair(_U1&&, _U2&&) [with _U2 = _U1; typename std::enable_if<(std::_PCC<true, _T1, _T2>::_MoveConstructiblePair<_U1, _U2>() && std::_PCC<true, _T1, _T2>::_ImplicitlyMoveConvertiblePair<_U1, _U2>()), bool>::type <anonymous> = _U2; _T1 = long long int; _T2 = std::pair<long long int, long long int>]'
  881 |         constexpr pair(_U1&& __x, _U2&& __y)
      |                   ^~~~
/usr/include/c++/14/bits/stl_pair.h:881:19: note:   template argument deduction/substitution failed:
/usr/include/c++/14/bits/stl_pair.h:880:38: error: no type named 'type' in 'struct std::enable_if<false, bool>'
  880 |                          bool>::type=true>
      |                                      ^~~~
/usr/include/c++/14/bits/stl_pair.h:869:9: note: candidate: 'template<class _U2, typename std::enable_if<std::__and_<std::is_pointer<long long int>, std::__not_<std::is_reference<_Tp> >, std::is_constructible<std::pair<long long int, long long int>, _U2>, std::__not_<std::is_constructible<std::pair<long long int, long long int>, const _U1&> >, std::__not_<std::is_convertible<_U2, std::pair<long long int, long long int> > > >::value, bool>::type <anonymous> > constexpr std::pair<_T1, _T2>::pair(__zero_as_null_pointer_constant, _U2&&, ...) [with typename std::enable_if<std::__and_<std::is_pointer<_Tp>, std::__not_<std::is_reference<_U1> >, std::is_constructible<_T2, _U2>, std::__not_<std::is_constructible<_T1, const _U1&> >, std::__not_<std::is_convertible<_U2, _T2> > >::value, bool>::type <anonymous> = _U2; _T1 = long long int; _T2 = std::pair<long long int, long long int>]'
  869 |         pair(__zero_as_null_pointer_constant, _U2&& __y, ...)
      |         ^~~~
/usr/include/c++/14/bits/stl_pair.h:869:9: note:   template argument deduction/substitution failed:
/usr/include/c++/14/bits/stl_pair.h:866:38: error: no type named 'type' in 'struct std::enable_if<false, bool>'
  866 |                              bool> = false>
      |                                      ^~~~~
/usr/include/c++/14/bits/stl_pair.h:856:9: note: candidate: 'template<class _U2, typename std::enable_if<std::__and_<std::is_pointer<long long int>, std::__not_<std::is_reference<_Tp> >, std::is_constructible<std::pair<long long int, long long int>, _U2>, std::__not_<std::is_constructible<std::pair<long long int, long long int>, const _U1&> >, std::is_convertible<_U2, std::pair<long long int, long long int> > >::value, bool>::type <anonymous> > constexpr std::pair<_T1, _T2>::pair(__zero_as_null_pointer_constant, _U2&&, ...) [with typename std::enable_if<std::__and_<std::is_pointer<_Tp>, std::__not_<std::is_reference<_U1> >, std::is_constructible<_T2, _U2>, std::__not_<std::is_constructible<_T1, const _U1&> >, std::is_convertible<_U2, _T2> >::value, bool>::type <anonymous> = _U2; _T1 = long long int; _T2 = std::pair<long long int, long long int>]'
  856 |         pair(__zero_as_null_pointer_constant, _U2&& __y, ...)
      |         ^~~~
/usr/include/c++/14/bits/stl_pair.h:856:9: note:   template argument deduction/substitution failed:
/usr/include/c++/14/bits/stl_pair.h:853:38: error: no type named 'type' in 'struct std::enable_if<false, bool>'
  853 |                              bool> = true>
      |                                      ^~~~
/usr/include/c++/14/bits/stl_pair.h:843:9: note: candidate: 'template<class _U1, typename std::enable_if<std::__and_<std::__not_<std::is_reference<_Tp> >, std::is_pointer<std::pair<long long int, long long int> >, std::is_constructible<long long int, _U1>, std::__not_<std::is_constructible<long long int, const _U1&> >, std::__not_<std::is_convertible<_U1, long long int> > >::value, bool>::type <anonymous> > constexpr std::pair<_T1, _T2>::pair(_U1&&, __zero_as_null_pointer_constant, ...) [with typename std::enable_if<std::__and_<std::__not_<std::is_reference<_U1> >, std::is_pointer<_T2>, std::is_constructible<_T1, _U1>, std::__not_<std::is_constructible<_T1, const _U1&> >, std::__not_<std::is_convertible<_U1, _T1> > >::value, bool>::type <anonymous> = _U1; _T1 = long long int; _T2 = std::pair<long long int, long long int>]'
  843 |         pair(_U1&& __x, __zero_as_null_pointer_constant, ...)
      |         ^~~~
/usr/include/c++/14/bits/stl_pair.h:843:9: note:   template argument deduction/substitution failed:
/usr/include/c++/14/bits/stl_pair.h:840:38: error: no type named 'type' in 'struct std::enable_if<false, bool>'
  840 |                              bool> = false>
      |                                      ^~~~~
/usr/include/c++/14/bits/stl_pair.h:830:9: note: candidate: 'template<class _U1, typename std::enable_if<std::__and_<std::__not_<std::is_reference<_Tp> >, std::is_pointer<std::pair<long long int, long long int> >, std::is_constructible<long long int, _U1>, std::__not_<std::is_constructible<long long int, const _U1&> >, std::is_convertible<_U1, long long int> >::value, bool>::type <anonymous> > constexpr std::pair<_T1, _T2>::pair(_U1&&, __zero_as_null_pointer_constant, ...) [with typename std::enable_if<std::__and_<std::__not_<std::is_reference<_U1> >, std::is_pointer<_T2>, std::is_constructible<_T1, _U1>, std::__not_<std::is_constructible<_T1, const _U1&> >, std::is_convertible<_U1, _T1> >::value, bool>::type <anonymous> = _U1; _T1 = long long int; _T2 = std::pair<long long int, long long int>]'
  830 |         pair(_U1&& __x, __zero_as_null_pointer_constant, ...)
      |         ^~~~
/usr/include/c++/14/bits/stl_pair.h:830:9: note:   template argument deduction/substitution failed:
/usr/include/c++/14/bits/stl_pair.h:827:38: error: no type named 'type' in 'struct std::enable_if<false, bool>'
  827 |                              bool> = true>
      |                                      ^~~~
/usr/include/c++/14/bits/stl_pair.h:789:28: note: candidate: 'template<class _U1, class _U2, typename std::enable_if<(std::_PCC<((! std::is_same<long long int, _U1>::value) || (! std::is_same<st