题目
题目链接:
https://www.nowcoder.com/practice/e7cbabbf7e0a41ec98055ee5f3d33bbe
https://www.lintcode.com/problem/796
思路
Java代码
import java.util.*;
public class Solution {
/**
* 代码中的类名、方法名、参数名已经指定,请勿修改,直接返回方法规定的值即可
*
*
* @param vec string字符串ArrayList
* @param tar string字符串
* @return int整型
*/
public int open (ArrayList<String> vec, String tar) {
//BFS 注意 当前状态,能得到到的下一个状态列表如何得到
//比如0000的可以变化的下一个状态: 共4位,每一位取上一个值,下一个值
// [9000, 1000, 0900, 0100, 0090, 0010, 0009, 0001]
if ("0000".equals(tar)) return 0;
Set<String> locked = new HashSet<>();
for (String d : vec) {
locked.add(d);
if ("0000".equals(d)) return -1; //初始就被锁住了
}
Queue<String> q = new LinkedList<>();
q.add("0000");
Set<String> visited = new HashSet<>();
visited.add("0000");
int step = 0;
while (!q.isEmpty()) {
step++;
int size = q.size();
for (int i = 0; i < size; i++) {
String status = q.poll();
List<String> nexts = getNexts(status);
//比如0000的nexts: [9000, 1000, 0900, 0100, 0090, 0010, 0009, 0001]
for (String next : nexts) {
if (visited.contains(next) || locked.contains(next)) continue;
if (next.equals(tar)) return step;
q.add(next);
visited.add(next);
}
}
}
return -1;
}
//枚举status通过一次旋转得到的数字
public List<String> getNexts(String status) {
List<String> ans = new ArrayList<>();
char[] arr = status.toCharArray();
for (int i = 0; i < 4; i++) {
char x = status.charAt(i);
//上一个数
char prev = x == '0' ? '9' : (char)(x - 1);
arr[i] = prev;
ans.add(new String(arr));
//下一个数
char succ = x == '9' ? '0' : (char)(x + 1);
arr[i] = succ;
ans.add(new String(arr));
arr[i] = x;
}
return ans;
}
}
Go代码
package main
/**
* 代码中的类名、方法名、参数名已经指定,请勿修改,直接返回方法规定的值即可
*
*
* @param vec string字符串一维数组
* @param tar string字符串
* @return int整型
*/
func open(vec []string, tar string) int {
//BFS 注意 当前状态,能得到到的下一个状态列表如何得到
//比如0000的可以变化的下一个状态: 共4位,每一位取上一个值,下一个值
// [9000, 1000, 0900, 0100, 0090, 0010, 0009, 0001]
if tar == "0000" {
return 0
}
locked := map[string]bool{}
for _, d := range vec {
locked[d] = true
if d == "0000" {
return -1 //初始位置就被锁住了
}
}
q := []string{}
visited := map[string]bool{}
step := 0
q = append(q, "0000")
for len(q) > 0 {
step++
size := len(q)
qbak := []string{}
for i := 0; i < size; i++ {
status := q[i]
nexts := getNexts(status)
//比如0000的nexts: [9000, 1000, 0900, 0100, 0090, 0010, 0009, 0001]
for _, next := range nexts {
if next == tar {
return step
}
_, ok1 := locked[next]
_, ok2 := visited[next]
if ok1 || ok2 {
continue
}
qbak = append(qbak, next)
visited[next] = true
}
}
q = qbak
}
return -1
}
// 枚举status通过一次旋转得到的数字
func getNexts(status string) []string {
ans := []string{}
arr := make([]byte, 4)
for i := 0; i < 4; i++ {
arr[i] = status[i]
}
for i := 0; i < 4; i++ {
x := arr[i]
//上一个
var prev byte = '9'
if x != '0' {
prev = x - 1
}
arr[i] = prev
ans = append(ans, string(arr))
//下一个
var succ byte = '0'
if x != '9' {
succ = x + 1
}
arr[i] = succ
ans = append(ans, string(arr))
arr[i] = x
}
return ans
}
PHP代码
<?php
/**
* 代码中的类名、方法名、参数名已经指定,请勿修改,直接返回方法规定的值即可
*
*
* @param vec string字符串一维数组
* @param tar string字符串
* @return int整型
*/
function open( $vec , $tar )
{
//BFS 注意 当前状态,能得到到的下一个状态列表如何得到
//比如0000的可以变化的下一个状态: 共4位,每一位取上一个值,下一个值
// [9000, 1000, 0900, 0100, 0090, 0010, 0009, 0001]
if($tar=='0000') return 0;
$locked =[];
foreach ($vec as $d){
if($d=='0000') return -1; //初始位置就被锁住了
$locked[$d] = $d;
}
$q = [0=>'0000'];
$visited = [];
$step = 0;
while (count($q) >0){
$step++;
$qbak = [];
$size =count($q);
for($i=0;$i<$size;$i++){
$status = $q[$i];
$nexts = getNexts($status);
//比如0000的nexts: [9000, 1000, 0900, 0100, 0090, 0010, 0009, 0001]
foreach ($nexts as $next){
if(isset($locked[$next])) continue;
if(isset($visited[$next])) continue;
if($next==$tar) return $step;
$qbak[count($qbak)] = $next;
$visited[$next] = $next;
}
}
$q =$qbak;
}
return -1;
}
// 枚举status通过一次旋转得到的数字
function getNexts($status){
$ans = [];
$arr = [];
for($i=0;$i<4;$i++){
$arr[$i] = $status[$i];
}
for($i=0;$i<4;$i++){
$x = $arr[$i];
//上一个
$prev='9';
if($x!='0'){
$prev = intval($x)-1;
$x.='';
}
$arr[$i] = $prev;
$str = '';
for($j=0;$j<4;$j++){
$str.=$arr[$j];
}
$ans[count($ans)] = $str;
//下一个
$succ = '0';
if($x!='9'){
$succ=intval($x)+1;
$succ.='';
}
$str = '';
$arr[$i] = $succ;
for($j=0;$j<4;$j++){
$str.=$arr[$j];
}
$ans[count($ans)] = $str;
$arr[$i] = $x;
}
return $ans;
}