Go: package main

import (
	"bufio"
	"fmt"
	"math"
	"os"
	"strconv"
)

func configure(scanner *bufio.Scanner) {
	scanner.Split(bufio.ScanWords)
	scanner.Buffer(make([]byte, 1000005), 1000005)
}
func getNextString(scanner *bufio.Scanner) string {
	scanned := scanner.Scan()
	if !scanned {
		panic("scan failed")
	}
	return scanner.Text()
}
func getNextInt(scanner *bufio.Scanner) int {
	i, _ := strconv.Atoi(getNextString(scanner))
	return i
}
func getNextInt64(scanner *bufio.Scanner) int64 {
	i, _ := strconv.ParseInt(getNextString(scanner), 10, 64)
	return i
}
func getNextFloat64(scanner *bufio.Scanner) float64 {
	i, _ := strconv.ParseFloat(getNextString(scanner), 64)
	return i
}
func main() {
	fp := os.Stdin
	wfp := os.Stdout
	extra := 0
	if os.Getenv("I") == "IronMan" {
		fp, _ = os.Open(os.Getenv("END_GAME"))
		extra = 100
	}
	scanner := bufio.NewScanner(fp)
	configure(scanner)
	writer := bufio.NewWriter(wfp)
	defer func() {
		r := recover()
		if r != nil {
			fmt.Fprintln(writer, r)
		}
		writer.Flush()
	}()
	solve(scanner, writer)
	for i := 0; i < extra; i++ {
		fmt.Fprintln(writer, "-----------------------------------")
		solve(scanner, writer)
	}
}
func solve(scanner *bufio.Scanner, writer *bufio.Writer) {
	n := getNextInt(scanner)
	s := getNextString(scanner)
	cc := makeGrid(9, 9)
	for i := 0; i < n-1; i++ {
		cc[s[i]-'0'-1][s[i+1]-'0'-1]++
	}
	p := make(permutation, 9)
	ans := make([]int, 9)
	p.dfs(0, 9, 0, ans, cc)
	for i := 0; i < 9; i++ {
		fmt.Fprint(writer, ans[i]+1)
		if i%3 == 2 {
			fmt.Fprintln(writer, "")
		}
	}
}
func makeGrid(h, w int) [][]int {
	index := make([][]int, h, h)
	data := make([]int, h*w, h*w)
	for i := 0; i < h; i++ {
		index[i] = data[i*w : (i+1)*w]
	}
	return index
}

var min int = math.MaxInt32

type permutation []int

func (p permutation) dfs(i, n int, used uint32, ans []int, cc [][]int) {
	if i == n {
		sum := getsum(p, cc)
		if min > sum {
			for i := 0; i < 9; i++ {
				ans[i] = p[i]
			}
			min = sum
		}
		return
	}
	for b := 0; b < 9; b++ {
		if used&(1<<uint(b)) != 0 {
			continue
		}
		p[i] = b
		p.dfs(i+1, n, used|(1<<uint(b)), ans, cc)
	}
}

func abs(a int) int {
	if a < 0 {
		return -a
	}
	return a
}
func getsum(p permutation, cc [][]int) int {
	sum := 0
	for i := 0; i < 9; i++ {
		for j := 0; j < 9; j++ {
			if i == j {
				continue
			}
			sum += (abs(i/3-j/3) + abs(i%3-j%3)) * cc[p[i]][p[j]]
		}
	}
	return sum
}

Python: def inpl(): return list(map(int, input().split()))
from collections import defaultdict
from itertools import combinations, permutations

N = int(input())
S = list(map(int, input()))

move = defaultdict(int)
b = S[0]
for i in range(N-1):
    a, b = S[i], S[i+1]
    move[(a, b)] += 1
    move[(b, a)] += 1

R = set(list(range(1, 10)))
bestscore = 10**10
bestans = "9"*9

def calc_br(bl, re):
    b0, b1, b2, b3 = bl
    r0, r1, r2, r3 = re
    stage3 = 0
    stage3 += move[(b0, r3)] + move[(b0, r0)] + 3*move[(b0, r1)] + 3*move[(b0, r2)]
    stage3 += move[(b1, r0)] + move[(b1, r1)] + 3*move[(b1, r2)] + 3*move[(b1, r3)]
    stage3 += move[(b2, r1)] + move[(b2, r2)] + 3*move[(b2, r3)] + 3*move[(b2, r0)]
    stage3 += move[(b3, r2)] + move[(b3, r3)] + 3*move[(b3, r0)] + 3*move[(b3, r1)]
    return stage3
    
    
def fliplr(black, bl, re):
    order = [bl[0], re[0], bl[1],
             re[3], black, re[1],
             bl[3], re[2], bl[2]]
    best = [9] * 9
    ixss = [[0, 1, 2, 3, 4, 5, 6, 7, 8],
            [2, 5, 8, 1, 4, 7, 0, 3, 6],
            [8, 7, 6, 5, 4, 3, 2, 1, 0],
            [6, 3, 0, 7, 4, 1, 8, 5, 2],
            [2, 1, 0, 5, 4, 3, 8, 7, 6],
            [0, 3, 6, 1, 4, 7, 2, 5, 8],
            [6, 7, 8, 3, 4, 5, 0, 1, 2],
            [8, 5, 2, 7, 4, 1, 6, 3, 0]]
    best = min(["".join([str(order[ix]) for ix in ixs]) for ixs in ixss])
    return best
    
    
for black in range(1, 10):
    remain = R.difference([black])
    for blue in combinations(remain, r=4):
        red = list(remain - set(blue))
        stage1 = 0
        for r in red:
            stage1 += move[(black, r)]
        for b in blue:
            stage1 += move[(black, b)] * 2
        for r1, r2 in combinations(red, 2):
            stage1 += move[(r1, r2)] * 2
    
        for bixs in [[0, 1, 2, 3], [0, 2, 3, 1], [0, 3, 1, 2]]:
            bl = [blue[bix] for bix in bixs]
            stage2 = (move[(bl[0], bl[1])] +
                      move[(bl[1], bl[2])] +
                      move[(bl[2], bl[3])] +
                      move[(bl[3], bl[0])] +
                      move[(bl[0], bl[2])]*2 +
                      move[(bl[1], bl[3])]*2)*2
            
            for re in permutations(red, 4):
                stage3 = calc_br(bl, re)
                score = stage1 + stage2 + stage3
                #if score == 11:
                #    print(black, bl, re)
                #print(stage1, stage2, stage3)
                if score <= bestscore:
                    if score < bestscore:
                        bestans = "9"*9
                    bestscore = score
                    bestans = min(bestans, fliplr(black, bl, re))
print("".join((map(str, bestans[:3]))))
print("".join((map(str, bestans[3:6]))))
print("".join((map(str, bestans[6:]))))

C++: #include<bits/stdc++.h>
using namespace std;
#define int long long
const int MOD = 1000000007LL;
const int INF = LLONG_MAX;

signed main(){
    
    int n; cin >> n;
    string s; cin >> s;
    int G[10][10] = {};
    for(int i = 1; i < n; i++){
        int cur = (int)(s[i - 1] - '0');
        int nxt = (int)(s[i] - '0');
        G[cur][nxt]++;
    }
    
    vector<int> vec(9);
    for(int i = 0; i < 9; i++) vec[i] = i + 1;
    int ans = INF;
    vector<int> ansV(9);
    
    do{
        int phone[3][3];
        for(int j = 0; j < 3; j++){
            for(int i = 0; i < 3; i++){
                phone[i][j] = vec[3 * j + i];
            }
        }

        int cost = 0;
        for(int ci = 0; ci < 3; ci++){
            for(int cj = 0; cj < 3; cj++){
                for(int ni = 0; ni < 3; ni++){
                    for(int nj = 0; nj < 3; nj++){
                        int cur = phone[ci][cj];
                        int nxt = phone[ni][nj];
                        int dis = (int)abs(ci - ni) + (int)abs(cj - nj);
                        cost += G[cur][nxt] * dis;
                    }
                }
            }
        }

        if(cost < ans){
            ans = cost;
            ansV = vec;
        }

    }while(next_permutation(vec.begin(), vec.end()));
    
    for(int j = 0; j < 3; j++){
        for(int i = 0; i < 3; i++){
            cout << ansV[3 * j + i];
        }
        cout << endl;
    }
    return 0;
}