技巧
    并查集
思路
    齐齐和司机分别开一个并查集
    合并会级联影响到的大炮
    rankMap维护当前集合中的个数
    若要消灭掉司机 需要齐齐 len(sijiRanlMap) - 1 次 操作 (齐齐现出手 所以要-1)
    然后升序排列一下齐齐的rankmap 算个差值就好
实现
package main

import (
	"bufio"
	. "fmt"
	"io"
	"os"
	"sort"
	"strings"
)

type E struct {
	x, y int
}

type UnionSet struct {
	eMap     map[E]bool
	faterMap map[E]E
	rankMap  map[E]int
}

func NewUnionSet() *UnionSet {
	return &UnionSet{
		make(map[E]bool),
		make(map[E]E),
		make(map[E]int),
	}
}

func (us *UnionSet) getHead(e E) E {
	if us.faterMap[e] == e {
		return e
	}
	head := us.getHead(us.faterMap[e])
	us.faterMap[e] = head
	return head
}
func (us *UnionSet) isSame(var1, var2 E) bool {
	return us.getHead(var1) == us.getHead(var2)
}
func (us *UnionSet) union(var1, var2 E) {
	if us.isSame(var1, var2) {
		return
	}
	fvar1, fvar2 := us.faterMap[var1], us.faterMap[var2]
	if us.rankMap[fvar1] >= us.rankMap[fvar2] {
		us.faterMap[fvar2] = fvar1
		us.rankMap[fvar1] += us.rankMap[fvar2]
		delete(us.rankMap, fvar2)
	} else {
		us.faterMap[fvar1] = fvar2
		us.rankMap[fvar2] += us.rankMap[fvar1]
		delete(us.rankMap, fvar1)
	}

}

// 8方向
var d = [8][2]int{{1, 0}, {-1, 0}, {0, 1}, {0, -1}, {-1, -1}, {1, 1}, {-1, 1}, {1, -1}}

func merge(uset *UnionSet) {
	for key, _ := range uset.eMap {
		for i := 0; i < 8; i++ {
			if _, ok := uset.eMap[E{key.x + d[i][0], key.y + d[i][1]}]; ok {
				uset.union(key, E{key.x + d[i][0], key.y + d[i][1]})
			}
		}
	}
}

func NC14698(_r io.Reader, _w io.Writer) {
	in, out := bufio.NewReader(_r), bufio.NewWriter(_w)
	defer out.Flush()
	var m int
	Fscan(in, &m)
	SiJi := [4][]string{}
	sijiUset := NewUnionSet()
	for i := 0; i < 4; i++ {
		var line string
		Fscan(in, &line)
		SiJi[i] = strings.Split(line, "")
		for j := 0; j < m; j++ {
			if SiJi[i][j] == "*" {
				e := E{i, j}
				sijiUset.eMap[e] = true
				sijiUset.faterMap[e] = e
				sijiUset.rankMap[e] = 1
			}
		}
	}

	QiQi := [4][]string{}
	qiqiUset := NewUnionSet()
	for i := 0; i < 4; i++ {
		var line string
		Fscan(in, &line)
		QiQi[i] = strings.Split(line, "")
		for j := 0; j < m; j++ {
			if QiQi[i][j] == "*" {
				e := E{i, j}
				qiqiUset.eMap[e] = true
				qiqiUset.faterMap[e] = e
				qiqiUset.rankMap[e] = 1
			}
		}
	}
	merge(sijiUset)
	merge(qiqiUset)

	if len(qiqiUset.rankMap) < len(sijiUset.rankMap) {
		Fprintln(out, -1)
	} else {
		a := make([]int, len(qiqiUset.rankMap))
		k := 0

		total := 0
		for _, v := range qiqiUset.rankMap {
			a[k] = v
			total += v
			k++
		}
		sort.Ints(a)

		tmp := 0
		for i := 0; i < len(sijiUset.rankMap)-1; i++ {
			tmp += a[i]
		}
		Fprintln(out, total-tmp)
	}
}

func main() {
	NC14698(os.Stdin, os.Stdout)
}