結果
問題 | No.5007 Steiner Space Travel |
ユーザー |
![]() |
提出日時 | 2025-01-30 03:55:35 |
言語 | Go (1.23.4) |
結果 |
AC
|
実行時間 | 447 ms / 1,000 ms |
コード長 | 4,900 bytes |
コンパイル時間 | 14,141 ms |
コンパイル使用メモリ | 237,796 KB |
実行使用メモリ | 54,108 KB |
スコア | 7,767,958 |
最終ジャッジ日時 | 2025-01-30 03:56:04 |
合計ジャッジ時間 | 27,586 ms |
ジャッジサーバーID (参考情報) |
judge2 / judge3 |
純コード判定しない問題か言語 |
(要ログイン)
ファイルパターン | 結果 |
---|---|
other | AC * 30 |
ソースコード
package mainimport . "fmt"import "math/rand"import "sort"const ALPHA = 5func dist(a,b []int, i int, c,d []int, j int) int {dx := a[i] - c[j]dy := b[i] - d[j]return dx*dx + dy*dy}func min(a, b int) int {if a < b {return a}return b}func max(a, b int) int {return a+b-min(a,b)}func main() {var n, m intScan(&n, &m)a := make([]int, n)b := make([]int, n)for i := range a {Scan(&a[i],&b[i])}c := make([]int, m+1)d := make([]int, m+1)h := make([][]int, 1001)hh := make([][]int, 1001)for i := range h {h[i] = make([]int, 1001)hh[i] = make([]int, 1001)}for i, x := range a {y := b[i]hh[max(0,y-100)][max(0,x-100)]++if x+101<=1000 {hh[max(0,y-100)][x+101]--}if y+101<=1000 {hh[y+101][max(0,x-100)]--}if x+101<=1000&&y+101<=1000 {hh[y+101][x+101]++}}for i, row := range hh {xx := 0for j, vhh := range row {xx += vhhh[i][j] = xxif i > 0 {h[i][j] += h[i-1][j]}hh[i][j] = 0}}id := 0area := [][]int{}for i, row := range h {for j, vh := range row {if vh == 0 || hh[i][j] != 0 {continue}id++var cnt, yy, xx intdfs := []int{i, j}for len(dfs) > 0 {y,x:=dfs[len(dfs)-2],dfs[len(dfs)-1]dfs = dfs[:len(dfs)-2]if h[y][x] != vh || hh[y][x] != 0 {continue}cnt++yy += yxx += xhh[y][x] = idif x > 0 {dfs = append(dfs, y,x-1)}if x < 1000 {dfs = append(dfs, y,x+1)}if y > 0 {dfs = append(dfs, y-1,x)}if y < 1000 {dfs = append(dfs, y+1,x)}}yy = min(1000, max(0, yy/cnt))xx = min(1000, max(0, xx/cnt))area = append(area, []int{vh, cnt, yy, xx})}}sort.Slice(area, func(i, j int) bool {return area[i][0]>area[j][0]})// println(Sprintf("%#v", area))for i := range c {c[i] = (i%3+1)*250d[i] = (i/3+1)*250}c[m/2] = c[m]d[m/2] = d[m]c = c[:m]d = d[:m]cc := 0for _, e := range area {ok := truefor i := 0; i < cc; i++ {dx := c[i]-e[3]dy := d[i]-e[2]ok = ok && (dx*dx+dy*dy>100*100)}if ok {c[cc] = e[3]d[cc] = e[2]cc++if cc == m {break}}}path := make([][][]int, n+m)for i := range path {path[i] = make([][]int, n+m)for j := range path[i] {switch {case i == j:path[i][j] = []int{ 0, j }case i < n && j < n:path[i][j] = []int{ALPHA*ALPHA*dist(a,b,i,a,b,j),j,}case i < n:path[i][j] = []int{ALPHA*dist(a,b,i,c,d,j-n),j,}case j < n:path[i][j] = []int{ALPHA*dist(c,d,i-n,a,b,j),j,}default:path[i][j] = []int{dist(c,d,i-n,c,d,j-n),j,}}}}for i := 0; i < n+m; i++ {for j := 0; j < n+m; j++ {if i == j {continue}for k := 0; k < n+m; k++ {if i==k || j==k {continue}if x := path[i][k][0]+path[k][j][0]; x < path[i][j][0] {path[i][j][0] = xpath[i][j][1] = k}}}}p := []int{0}for i := 0; i < n; i++ {p = append(p, (i+1)%n)}calc := func(p []int) int {sc := 0for i := 0; i < n; i++ {sc += path[p[i]][p[i+1]][0]}return sc}bestSc := calc(p)bestP := make([]int, len(p))copy(bestP, p)for kk := 0; kk < 40; kk++ {for cc, changed := 0, true; changed && cc < 100; cc++ {changed = false// 2-opt ?for i := 1; i < n; i++ {for j := i+1; j < n; j++ {s0 := path[p[i-1]][p[i]][0] +path[p[j]][p[j+1]][0]s1 := path[p[i-1]][p[j]][0] +path[p[i]][p[j+1]][0]if s1 < s0 {for f,e := i,j; f < e; f,e=f+1,e-1 {p[f],p[e] = p[e],p[f]}changed = true}}}// 3-opt ?for i := 1; i < n; i++ {for j := i+1; j < n; j++ {for k := j+2; k < n; k++ {s0 := path[p[i-1]][p[i]][0] +path[p[j]][p[j+1]][0] +path[p[k]][p[k+1]][0]s1 := path[p[i-1]][p[j]][0] +path[p[i]][p[k]][0] +path[p[j+1]][p[k+1]][0]if s1 < s0 {for f,e := i,j; f < e; f,e=f+1,e-1 {p[f],p[e] = p[e],p[f]}for f,e := j+1,k; f < e; f,e=f+1,e-1 {p[f],p[e] = p[e],p[f]}changed = true}}}}}if sc := calc(p); sc < bestSc {bestSc = sccopy(bestP, p)}rand.Shuffle(n-1, func(i, j int) {p[i+1],p[j+1] = p[j+1],p[i+1]})}p = bestPt := []int{1}r := []int{1}var add func(i, j int)add = func(i, j int) {rt := path[i][j]if rt[1] == j {if j < n {t = append(t, 1)r = append(r, j+1)} else {t = append(t, 2)r = append(r, j-n+1)}return}add(i, rt[1])add(rt[1], j)}for i := 0; i < n; i++ {add(p[i], p[i+1])}for i := range c {Println(c[i], d[i])}Println(len(t))for i := range t {Println(t[i], r[i])}}