[Offer收割]编程练习赛13 hihocoder 1504 (矩阵快速幂)
来源:互联网 发布:安徽省癌症数据 编辑:程序博客网 时间:2024/05/29 16:39
#1504 : 骑士游历
时间限制:10000ms
单点时限:1000ms
内存限制:256MB
- 样例输入
2 1 1
- 样例输出
12
描述
在8x8的国际象棋棋盘上给定一只骑士(俗称“马”)棋子的位置(R, C),小Hi想知道从(R, C)开始移动N步一共有多少种不同的走法。
输入
第一行包含三个整数,N,R和C。
对于40%的数据, 1 <= N <= 1000000
对于100%的数据, 1 <= N <= 1000000000 1 <= R, C <= 8
输出
从(R, C)开始走N步有多少种不同的走法。由于答案可能非常大,你只需要输出答案模1000000007的余数。
题目链接:https://hihocoder.com/problemset/problem/1504
题目分析:典型的矩阵快速幂问题,由于棋盘大小只有8*8,可以将一个点的横纵坐标hash成一个值,建一个64*64的矩阵来表示点的转移
import java.util.*;import java.io.*;public class Main { public static final long MOD = 1000000007; public static final int CON = 64; public static int[] dx = {1, 2, 2, 1, -1, -2, -2, -1}; public static int[] dy = {-2, -1, 1, 2, 2, 1, -1, -2}; public static int n, r, c; static class myScanner { public BufferedReader br; public StringTokenizer st; public myScanner(InputStream in) { br = new BufferedReader(new InputStreamReader(in)); st = new StringTokenizer(""); } public String nextLine() { try { return br.readLine(); } catch(IOException e) { return null; } } public boolean hasNext() { while(!st.hasMoreTokens()) { String s = nextLine(); if (s == null) { return false; } st = new StringTokenizer(s); } return true; } public String next() { hasNext(); return st.nextToken(); } public int nextInt() { return Integer.parseInt(next()); } } static class Matrix { public int n, m; public long[][] mat; public Matrix(int n, int m) { this.n = n; this.m = n; mat = new long[n][m]; for (int i = 0; i < n; i ++) { Arrays.fill(mat[i], 0); } } public static Matrix mul(Matrix a, Matrix b) { Matrix ans = new Matrix(a.n, b.m); for (int i = 0; i < a.n; i ++) { for (int j = 0; j < b.m; j ++) { for (int k = 0; k < a.m; k ++) { ans.mat[i][j] = (ans.mat[i][j] + a.mat[i][k] * b.mat[k][j]) % MOD; } } } return ans; } public static Matrix pow(Matrix a, int n) { Matrix ans = new Matrix(a.n, a.n); for (int i = 0; i < a.n; i ++) { ans.mat[i][i] = 1; } while (n != 0) { if ((n & 1) == 1) { ans = mul(ans, a); } a = mul(a, a); n >>= 1; } return ans; } } public static Matrix pre() { Matrix ans = new Matrix(64, 64); for (int i = 0; i < 8; i ++) { for (int j = 0; j < 8; j ++) { for (int k = 0; k < 8; k ++) { int x = i + dx[k]; int y = j + dy[k]; if (x < 0 || y < 0 || x > 7 || y > 7) { continue; } ans.mat[i * 8 + j][x * 8 + y] = 1; } } } return ans; } public static void main(String[] args) { myScanner in = new myScanner(System.in); n = in.nextInt(); r = in.nextInt(); c = in.nextInt(); r --; c --; Matrix coef = pre(); Matrix ans = new Matrix(64, 64); ans.mat[r * 8 + c][r * 8 + c] = 1; ans = Matrix.mul(ans, Matrix.pow(coef, n)); long res = 0; for (int i = 0; i < 64; i ++) { for (int j = 0; j < 64; j ++) { res = (res + ans.mat[i][j]) % MOD; } } System.out.println(res); }}
0 0
- [Offer收割]编程练习赛13 hihocoder 1504 (矩阵快速幂)
- 【[Offer收割]编程练习赛13 D】骑士游历(矩阵快速幂模板)
- hihocoder [Offer收割]编程练习赛19
- hihocoder [Offer收割]编程练习赛24
- 【[Offer收割]编程练习赛23 C】【矩阵快速幂】H国的身份证号码II
- 【hihocoder [Offer收割]编程练习赛9 D】【简单DP】矩阵填数
- [Offer收割]编程练习赛1 hihocoder 1268 九宫 (DFS)
- [Offer收割]编程练习赛2 hihocoder 1273 (DFS + 状压)
- hihoCoder[Offer收割]编程练习赛2题目解析
- hihoCoder 1285 [Offer收割]编程练习赛3-3
- hihoCoder[Offer收割]编程练习赛3题目解析
- hihoCoder[Offer收割]编程练习赛1题目解析
- hihocoder[Offer收割]编程练习赛3及参考
- hihocoder[Offer收割]编程练习赛5及参考
- hihocoder[Offer收割]编程练习赛6及参考
- hihocoder-- 热门号码([Offer收割]编程练习赛37)
- hihocoder[Offer收割]编程练习赛41:01间隔矩阵(单调栈求最大子矩形面积)
- [Offer收割]编程练习赛1 hihocoder 1269 优化延迟 (二分+优先权队列)
- Unity3d入门
- Qt Designer 2048 Game
- 多表查询
- 区间k大数查询
- 《Python 机器学习及实践--从零开始通往kaggle竞赛之路》笔记
- [Offer收割]编程练习赛13 hihocoder 1504 (矩阵快速幂)
- CODE[VS]1043 方格取数(多进程DP)
- 常用linux命令(3)
- 关于接入百度语音的总结
- API Guide:绪论-设备兼容性
- pat 1061. Dating
- 动态规划练习-06(登山)
- pacp_loop函数的使用
- poj2528 Mayor's posters 线段树+离散化(经典)