MOOC数据结构(下)(自主模式)-玩具(Toy)

2023-10-24 20:30

本文主要是介绍MOOC数据结构(下)(自主模式)-玩具(Toy),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

玩具(Toy)


Description

ZC God is best at logical reasoning. One day, he talks about his childhood digital toys.

The toy is like a Rubik's cube, but not a Rubik's cube. Specifically, it is not a 3 * 3 * 3 structure, but a 4 * 2 structure.

According to the play of the toy, we can repeatedly transform it in the following three ways:

A. Exchange the upper and lower lines. For example, the result of the transformation of Figure (a) is shown in Figure (b).

B. Loop right shift (ZC God knows what this means from an early age). For example, the result of the transformation of Figure (b) is shown in Figure (c).

C. The center rotates clockwise. For example, the result of the transformation of Figure (c) is shown in Figure (d).

ZC God is a genius in this respect. He often has a hand that has not dried his nose, the other hand has quickly restored the toy in any state to the initial state shown in Figure (a). In the year when the material was extremely scarce, ZC God had only one such toy; today, the material is extremely rich, and you have many toys in different states. Now, please restore them all.

Input

The first line is a positive integer, which is the total number of Rubik's cube toys you have.

In each one of the following N lines, 8 positive integers, i.e. an arrangement of 1~8, are included, indicating the current state of the toy.

Here, the representation rule of the cube state is that the first four numbers represent the first line of the cube from left to right, and the last four numbers represent the second line from right to left. For example, the initial state is expressed as "1 2 3 4 5 6 7 8".

Output

A total of N lines, each line containing an integer, in turn corresponding to the minimum number of transform needs to be performed to restore each toy.

In particular, if a toy is not recoverable, the corresponding line outputs -1.

Example

Input

2
1 2 3 4 5 6 7 8
8 6 3 5 4 2 7 1

Output

0
2

Restrictions

For 60% of the data, N = 1

For 100% of the data,1 <= N <= 1,000

Time: 1 sec

Memory: 20 MB

Hints

State transition diagram and its search

描述

ZC神最擅长逻辑推理,一日,他给大家讲述起自己儿时的数字玩具。

该玩具酷似魔方,又不是魔方。具体来说,它不是一个3 * 3 * 3的结构,而是4 * 2的结构。

按照该玩具约定的玩法,我们可反复地以如下三种方式对其做变换:

A. 交换上下两行。比如,图(a)经此变换后结果如图(b)所示。

B. 循环右移(ZC神从小就懂得这是什么意思的)。比如,图(b)经此变换后结果如图(c)所示。

C. 中心顺时针旋转。比如,图(c)经此变换后结果如图(d)所示。

ZC神自小就是这方面的天才,他往往是一只手还没揩干鼻涕,另一只手已经迅速地将处于任意状态的玩具复原至如图(a)所示的初始状态。物质极其匮乏的当年,ZC神只有一个这样的玩具;物质极大丰富的今天,你已拥有多个处于不同状态的玩具。现在,就请将它们全部复原吧。

输入

第一行是一个正整数,即你拥有的魔方玩具总数N。

接下来共N行,每行8个正整数,是1~8的排列,表示该玩具的当前状态。

这里,魔方状态的表示规则为:前四个数自左向右给出魔方的第一行,后四个数自右向左给出第二行。比如,初始状态表示为“1 2 3 4 5 6 7 8”。

输出

共N行,各含一个整数,依次对应于复原各玩具所需执行变换的最少次数。

特别地,若某个玩具不可复原,则相应行输出-1。

样例

见英文题面

限制

对于60%的数据,N = 1

对于100%的数据,1 <= N <= 1,000

时间:1 sec

空间:20MB

提示

状态转换图及其搜索

 

C++:

/*@Date    : 2018-03-09 13:58:53@Author  : 酸饺子 (changzheng300@foxmail.com)@Link    : https://github.com/SourDumplings@Version : $Id$
*//*
https://dsa.cs.tsinghua.edu.cn/oj/problem.shtml?id=1151
一共有8!=40320中状态,通过哈希表建立映射(康托展开)。
大体思路就是从原始状态开始通过三种操作的反向给出一切可以达到的状态,
通过BFS进行探索。
如果某个状态已经实现过则回溯,因为BFS第一遍到达该结点的步数就是最短路径
故需要记录每个状态的访问标记和需要达到的最小步数,假设步数为-1即为未访问过。
对于逆康托要保存康托的结果,大大提高效率*/#include <iostream>
#include <cstdio>
#include <cstring>using namespace std;static const int MAX = 40321;static const int factorial[8] = {1, 1, 2, 6, 24, 120, 720, 5040};struct stateInfo
{bool valid = false;int A[8];int step = -1;
};static stateInfo data[MAX];struct Queue
{int data[MAX];int front = 0, end = 0;int pop(){int temp = front;front = (front + 1) % MAX;return data[temp];}void push(int i){data[end] = i;end = (end + 1) % MAX;return;}bool empty() { return front == end; }
};template <typename T>
void print(T A[], int n)
{for (int i = 0; i != n; ++i)cout << A[i] << ' ';putchar('\n');return;
}void check_enq(int w, int v, Queue &Q)
{if (data[w].step == -1){data[w].step = data[v].step + 1;Q.push(w);}return;
}int contor(int A[], int n)
{int res = 0;for (int i = 0; i != n; ++i){int smaller = 0;for (int j = i + 1; j != n; ++j){if (A[j] < A[i]) ++smaller;}res += smaller * factorial[n-i-1];}return res;
}void re_contor(int stateNo, int n)
{int temp;bool used[n];memset(used, false, sizeof(used));int tempStateNo = stateNo;for (int i = 0; i != n - 1; ++i){temp = tempStateNo / factorial[n-i-1];int rank = 0;for (int j = 1; j != n + 1; ++j){if (!used[j-1])++rank;if (rank == temp + 1){data[stateNo].A[i] = j;used[j-1] = true;break;}}tempStateNo %= factorial[n-i-1];}for (int i = 0; i != n; ++i){if (!used[i]){data[stateNo].A[n-1] = i + 1;break;}}data[stateNo].valid = true;return;
}void swap(int &a, int &b)
{int temp = a;a = b;b = temp;return;
}// 上下互换
int op1(int A_o[])
{int A[8];memcpy(A, A_o, sizeof(A));swap(A[0], A[7]);swap(A[1], A[6]);swap(A[2], A[5]);swap(A[3], A[4]);int res = contor(A, 8);memcpy(data[res].A, A, sizeof(A));data[res].valid = true;return res;
}// 循环左移
int op2(int A_o[])
{int A[8];memcpy(A, A_o, sizeof(A));int temp1 = A[0], temp2 = A[7];A[0] = A[1];A[1] = A[2];A[2] = A[3];A[7] = A[6];A[6] = A[5];A[5] = A[4];A[3] = temp1;A[4] = temp2;int res = contor(A, 8);memcpy(data[res].A, A, sizeof(A));data[res].valid = true;return res;
}// 逆时针旋转
int op3(int A_o[])
{int A[8];memcpy(A, A_o, sizeof(A));int temp = A[1];A[1] = A[2];A[2] = A[5];A[5] = A[6];A[6] = temp;int res = contor(A, 8);memcpy(data[res].A, A, sizeof(A));data[res].valid = true;return res;
}void BFS()
{Queue Q;Q.push(0);data[0].step = 0;while (!Q.empty()){int v = Q.pop();if (!data[v].valid) re_contor(v, 8);// printf("reached stateNo = %d: ", v);// print(data[v].A, 8);int w1 = op1(data[v].A), w2 = op2(data[v].A), w3 = op3(data[v].A);check_enq(w1, v, Q);check_enq(w2, v, Q);check_enq(w3, v, Q);}return;
}int main(int argc, char const *argv[])
{BFS();int N;scanf("%d", &N);for (int i = 0; i != N; ++i){int A[8];for (int j = 0; j != 8; ++j) scanf("%d", &A[j]);int stateNo = contor(A, 8);// printf("stateNo = %d for A: \n", stateNo);// print(A, 8);printf("%d\n", data[stateNo].step);}return 0;
}

 

这篇关于MOOC数据结构(下)(自主模式)-玩具(Toy)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/277601

相关文章

Redis Cluster模式配置

《RedisCluster模式配置》:本文主要介绍RedisCluster模式配置,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友参考下吧... 目录分片 一、分片的本质与核心价值二、分片实现方案对比 ‌三、分片算法详解1. ‌范围分片(顺序分片)‌2. ‌哈希分片3. ‌虚

RabbitMQ工作模式中的RPC通信模式详解

《RabbitMQ工作模式中的RPC通信模式详解》在RabbitMQ中,RPC模式通过消息队列实现远程调用功能,这篇文章给大家介绍RabbitMQ工作模式之RPC通信模式,感兴趣的朋友一起看看吧... 目录RPC通信模式概述工作流程代码案例引入依赖常量类编写客户端代码编写服务端代码RPC通信模式概述在R

SQL Server身份验证模式步骤和示例代码

《SQLServer身份验证模式步骤和示例代码》SQLServer是一个广泛使用的关系数据库管理系统,通常使用两种身份验证模式:Windows身份验证和SQLServer身份验证,本文将详细介绍身份... 目录身份验证方式的概念更改身份验证方式的步骤方法一:使用SQL Server Management S

Redis高可用-主从复制、哨兵模式与集群模式详解

《Redis高可用-主从复制、哨兵模式与集群模式详解》:本文主要介绍Redis高可用-主从复制、哨兵模式与集群模式的使用,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝... 目录Redis高可用-主从复制、哨兵模式与集群模式概要一、主从复制(Master-Slave Repli

一文带你搞懂Redis Stream的6种消息处理模式

《一文带你搞懂RedisStream的6种消息处理模式》Redis5.0版本引入的Stream数据类型,为Redis生态带来了强大而灵活的消息队列功能,本文将为大家详细介绍RedisStream的6... 目录1. 简单消费模式(Simple Consumption)基本概念核心命令实现示例使用场景优缺点2

Nginx location匹配模式与规则详解

《Nginxlocation匹配模式与规则详解》:本文主要介绍Nginxlocation匹配模式与规则,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教... 目录一、环境二、匹配模式1. 精准模式2. 前缀模式(不继续匹配正则)3. 前缀模式(继续匹配正则)4. 正则模式(大

Linux系统配置NAT网络模式的详细步骤(附图文)

《Linux系统配置NAT网络模式的详细步骤(附图文)》本文详细指导如何在VMware环境下配置NAT网络模式,包括设置主机和虚拟机的IP地址、网关,以及针对Linux和Windows系统的具体步骤,... 目录一、配置NAT网络模式二、设置虚拟机交换机网关2.1 打开虚拟机2.2 管理员授权2.3 设置子

C#数据结构之字符串(string)详解

《C#数据结构之字符串(string)详解》:本文主要介绍C#数据结构之字符串(string),具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教... 目录转义字符序列字符串的创建字符串的声明null字符串与空字符串重复单字符字符串的构造字符串的属性和常用方法属性常用方法总结摘

SpringBoot如何通过Map实现策略模式

《SpringBoot如何通过Map实现策略模式》策略模式是一种行为设计模式,它允许在运行时选择算法的行为,在Spring框架中,我们可以利用@Resource注解和Map集合来优雅地实现策略模式,这... 目录前言底层机制解析Spring的集合类型自动装配@Resource注解的行为实现原理使用直接使用M

C#原型模式之如何通过克隆对象来优化创建过程

《C#原型模式之如何通过克隆对象来优化创建过程》原型模式是一种创建型设计模式,通过克隆现有对象来创建新对象,避免重复的创建成本和复杂的初始化过程,它适用于对象创建过程复杂、需要大量相似对象或避免重复初... 目录什么是原型模式?原型模式的工作原理C#中如何实现原型模式?1. 定义原型接口2. 实现原型接口3