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

const int N=16;

int ones[1 << N],map[1 << N];
int state[N][N];
char str[N][N + 1];

int bstate[N * N + 1][N][N],bstate2[N * N + 1][N][N];
char bstr[N * N + 1][N][N + 1];

int lowbit(int x)
{
    return x & -x;
}



void draw(int x, int y, int c)
{
    str[x][y] = c + 'A';

    for(int i = 0; i < N; i ++ )
    {
        state[x][i] &= ~(1 << c);
        state[i][y] &= ~(1 << c);
    }

    int mx = x / 4 * 4; 
    int my = y / 4 * 4;
    for(int i = 0; i < 4; i ++ )
        for(int j = 0; j < 4; j ++ )
            state[mx + i][my + j] &= ~(1 << c);     

    state[x][y] = 1 << c;

}

bool remove(int cnt)
{
    memcpy(state, bstate[cnt], sizeof state);
    memcpy(str, bstr[cnt], sizeof str);
    return false;
}

bool dfs(int cnt)
{
    if(cnt == 0)
        return true;

    int kcnt=cnt;
    memcpy(bstate[kcnt], state, sizeof state);
    memcpy(bstr[kcnt], str, sizeof str);

    // 对于每个空格不能填返回false 只能填一个则填
    for(int i = 0; i < N; i ++ )
        for(int j = 0; j < N; j ++ )
        {
            if(str[i][j] == '-')
            {
                int s = state[i][j];

                if(s == 0)
                    return remove(kcnt);

                if(ones[s] == 1)
                {
                    draw(i, j, map[s]);
                    cnt--;
                }
            }      
        }

    // 对于每一行/列/16宫格如果有一个字母不能填返回false,某个字母只有一种填法则填
    for(int i = 0; i < N; i ++ )
    {
        int sor = 0;//记录(j之前)可选方案的并集
        int drawn = 0;//记录所有已填的字母
        int sand = (1 << N) - 1;
        //记录该行所有可选方案中只出现1或0次的字母,假设全合法筛掉不合法

        for(int j = 0; j < N; j ++ )
        {
            int s = state[i][j];
            sand &= ~ (sor & s);
            sor |= s;
            if(str[i][j]!='-')
                drawn |= state[i][j];
        }

        if(sor != (1 << N) - 1)
            return remove(kcnt);

        for(int j = sand; j; j-=lowbit(j))
        {
            int t = lowbit (j);
            if((drawn & t) == 0)
                for(int k = 0; k < N; k ++ )
                    if(state[i][k] & t)
                    {
                        draw(i, k, map[t]);
                        cnt--;
                        break;
                    }           
        }
    }

    for(int i = 0; i < N; i ++ )
        {
            int sor = 0;//记录(j之前)可选方案的并集
            int drawn = 0;//记录所有已填的字母
            int sand = (1 << N) - 1;
            //记录该行所有可选方案中只出现1或0次的字母,假设全合法筛掉不合法

            for(int j = 0; j < N; j ++ )
            {
                int s = state[j][i];
                sand &= ~ (sor & s);
                sor |= s;
                if(str[j][i]!='-')
                    drawn |= state[j][i];
            }

            if(sor != (1 << N) - 1)
                return remove(kcnt);

            for(int j = sand; j; j-=lowbit(j))
            {
                int t = lowbit (j);
                if((drawn & t) == 0)
                    for(int k = 0;k < N; k ++ )
                        if(state[k][i] & t)
                        {
                            draw(k, i, map[t]);
                            cnt--;
                            break;
                        }           
            }
        }

    for(int i = 0; i < N; i ++ )
    {
        int sor = 0;//记录(j之前)可选方案的并集
        int drawn = 0;//记录所有已填的字母
        int sand = (1 << N) - 1;
        //记录该行所有可选方案中只出现1或0次的字母,假设全合法筛掉不合法

        for(int j = 0; j < N; j ++ )
        {
            int sx = i / 4 * 4, sy = i % 4 * 4;
            // (i / 4 * 4, i % 4 * 4) 即当前 4 * 4 方格的左上角坐标
            int dx = j / 4 ,dy = j % 4;  
            int s = state[sx + dx][sy + dy];
            sand &= ~ (sor & s);
            sor |= s;
            if(str[sx + dx][sy + dy]!='-')
                drawn |= s;
        }

        if(sor != (1 << N) - 1)
            return remove(kcnt);

        for(int j = sand; j; j-=lowbit(j))
        {
            int t = lowbit (j);
            if((drawn & t) == 0)
                for(int k = 0;k < N; k ++ )
                {
                    int sx = i / 4 * 4, sy = i % 4 * 4;
                    int dx = k / 4, dy = k % 4;
                    if (state[sx + dx][sy + dy] & t)
                    {
                        draw(sx + dx, sy + dy, map[t]);
                        cnt -- ;
                        break;
                    }
                }         
        }
    }

    if(cnt == 0)
        return true;
    // 优先填最少方案数的格子

    int x,y,minv=100;
    for(int i = 0; i < N; i ++ )
        for(int j = 0; j < N; j ++)
            if(str[i][j] == '-' && ones[state[i][j]] < minv)
            {
                x = i;
                y = j;
                minv = ones[state[i][j]];
            }

    memcpy(bstate2[kcnt], state, sizeof state);

    for(int i = state[x][y]; i; i -= lowbit(i))
    {
        memcpy(state, bstate2[kcnt], sizeof state);
        draw(x, y, map[lowbit(i)]);
        if (dfs(cnt - 1)) return true;
    }

    return remove(kcnt) ;
}

int main()
{

    for(int i = 0; i < 1 << N; i ++ )
        for(int j = i; j; j -= lowbit(j))
            ones[i] ++;

    for(int i = 0; i < N; i ++ )
            map[1 << i] = i;



    while(cin >> str[0])
    {
        for(int i = 1; i < N; i ++ )
            cin >> str[i];

        for(int i = 0; i < N; i ++ )
            for(int j = 0; j < N; j ++ )
                state[i][j] = (1 << N) - 1;
        int cnt = 0;
        for(int i = 0; i < N; i ++ )
            for(int j = 0; j < N; j ++ )
            {
                if(str[i][j]!='-')
                    draw(i, j, str[i][j]-'A');
                else
                    cnt ++ ;
            }

        dfs(cnt);

        for(int i = 0; i < N; i ++ )
            cout << str[i] << endl;
        cout << endl;

    }
}