#define _CRT_SECURE_NO_WARNINGS
#include <cstdio>
 
using namespace std;
 
template<class T> void gc(T &x)
{
    int s, k, m = 0;
    x = 0;
 
    k = getchar_unlocked();
 
    if (k == '-') s = 1;
    else if ('0' <= k && k <= '9')  x = k - '0';
 
    while (true)
    {
        k = getchar_unlocked();
 
        if (k < '0' || k > '9') break;
        x = x * 10 + k - '0';
    }
 
    if (m) x = -x;
}
 
template<class T> void pc_d(T x) {
    if(x < 0){
        x = -x;
        putchar_unlocked('-');
    }
    int i = 10;
    char output_buffer[10];
    do
    {
        output_buffer[--i] = (x % 10)+'0';
        x /= 10;
    }
    while (x);
 
    do
    {
        putchar_unlocked(output_buffer[i]);
    }
    while (++i<10);
}
 
int root(int p, int a[])
{
    if (p != a[p]) a[p] = root(a[p], a);
    return a[p];
}
 
int main()
{
    const int max = 200010;
 
    // 道路で連結する親代表都市
    int rdRoot[max];
 
    // 鉄道で連結する親代表都市
    int rwRoot[max];
 
    // 道路で連結する都市グループの末端
    int rdLeaf[max];
 
    // 道路で連結する都市グループ内の次の都市
    int rdNext[max];
 
    // 鉄道で連結する親代表都市が所属する 道路で連結する都市グループ
    int rwRootGrp[max];
 
    // 鉄道で連結する親代表都市が所属する 道路で連結する都市グループ内 カウント
    int rwRootGrpCnt[max];
 
    // 各都市のカウント
    int ans[max] = {0};
 
    int n, k, l;
    gc(n);
    gc(k);
    gc(l);
 
    // 親代表都市 初期化
    for (int i = 0; i < n; i++)
    {
        rdRoot[i] = i;
        rwRoot[i] = i;
 
        rdLeaf[i] = -1;
        rdNext[i] = -1;
        rwRootGrp[i] = 0;
        rwRootGrpCnt[i] = 0;
    }
 
    // 道路 親代表都市 設定
    for (int i = 0; i < k; i++)
    {
        int p, q;
        gc(p);
        gc(q);
 
        int pRoot = root(p - 1, rdRoot);
        int qRoot = root(q - 1, rdRoot);
 
        if (pRoot != qRoot)
        {
            // 配列インデックスが小さい方を親都市とする
            if (pRoot < qRoot) rdRoot[qRoot] = pRoot;
            else rdRoot[pRoot] = qRoot;
        }
    }
 
    // 鉄道 親代表都市 設定
    for (int i = 0; i < l; i++)
    {
        int r, s;
        gc(r);
        gc(s);
 
        int rRoot = root(r - 1, rwRoot);
        int sRoot = root(s - 1, rwRoot);
 
        if (rRoot != sRoot)
        {
            // 配列インデックスが小さい方を親都市とする
            if (rRoot < sRoot) rwRoot[sRoot] = rRoot;
            else rwRoot[rRoot] = sRoot;
        }
    }
 
    // 道路 都市グループ末端 設定
    for (int i = 0; i < n; i++)
    {
        int rd = root(i, rdRoot);
        if (i == rd) rdLeaf[i] = i;
        else
        {
            rdNext[i] = rdLeaf[rd];
 
            // 連結の順番に関係無く、配列のインデックスの順番
            rdLeaf[rd] = i;
        }
    }
 
    // 道路 都市グループ
    int rdGrp = 0;
 
    // 都市
    for (int i = 0; i < n; i++)
    {
        // 鉄道で連結していない都市は対象ではない
        if (rdLeaf[i] >= 0)
        {
            // 道路 都市グループ
            rdGrp++;
 
            // 次の都市をたどる
            // 1.カウントを鉄道の親代表都市に集約する
            for (int j = rdLeaf[i]; j >= 0; j = rdNext[j])
            {
                int rw = root(j,rwRoot);
                if (rwRootGrp[rw] == rdGrp)
                {
                    rwRootGrpCnt[rw]++;
                }
                else
                {
                    rwRootGrp[rw] = rdGrp;
                    rwRootGrpCnt[rw] = 1;
                }
            }
 
            // 2.カウントを鉄道の親代表都市から子都市に配る
            for (int j = rdLeaf[i]; j >= 0; j = rdNext[j])
            {
                int rw = root(j,rwRoot);
                ans[j] = rwRootGrpCnt[rw];
            }
        }
    }
 
    for (int i = 0; i < n - 1; i++)
    {
        pc_d(ans[i]);
        putchar_unlocked(' ');
    }
 
    pc_d(ans[n - 1]);
    putchar_unlocked('\n');
 
    return 0;
}

Measured memory_bytes: 6144