豪哇呦 發表於 2019-10-26 23:17:00

P2-汇编语言

<p><span style="font-size: 15px">通过阅读本文,您的收获可能有:理解递归程序的本质,知道如何用汇编语言去写dfs,知道P2考试重点要考察的内容。更优质的内容可以移步roife.github.io,roife yyds!</span></p>
<p>省流助手:过P2需要熟练掌握递归程序的汇编实现、数组(含二维数组)的操作、把C程序翻译成汇编,另外要会用断点调试 or 有优秀的静态调试能力,最好事先熟悉一下已经学过的数据结构和算法。</p>
<p><span style="font-size: 15px">听说我押中了正考两题和后面的补考两题hhh</span></p>
<p><span style="font-size: 15px">upd:19级新考了素数判断,约瑟夫环,快排,可见程设课难度的题都有可能放P2考。另外似乎无脑压栈会导致TLE了,所以压栈的时候要思考一下,哪些是必须压栈的,哪些是可以变的,以及是否能提前算好栈大小,而不是用一个格子就减掉一个格子的位置。</span></p>
<p><span style="font-size: 15px">upd: 20级同学的话可能会面对一个造数据的神,上面提到的问题可能真的要仔细思考一下。B站搜索咕咕香,可以找到该神的汇编程序设计补充教程,他会在视频中演示如何用汇编打一棵平衡树等操作。</span></p>
<p><strong style="font-size: 18px">课下测试部分:</strong></p>
<p><span style="font-size: 15px">今天晚上才刚开始写作业,目前只写了前两个,感觉和P1课上的时候一样,代码写得慢。基本的对二维数组的操作和多重循环中的例行公事部分(修改计数器,条件判断)有时候会忘记。</span></p>
<p><span style="font-size: 15px">矩阵乘法:</span></p>
<p><span style="font-size: 15px">基本的二维数组操作,在做之前我特意比较了一下P2教程中的二维数组操作和预习教程中的二维数组操作,发现P2写的类似于使用do while型的循环,有一定的优势,比如do while省标签个数,代码量也相对于for循环少。出现的问题有:循环实现慢(老毛病),写错了一个换行向量的判断条件(比较对象写错了),还有多重循环有一处没有刷新计数变量。此处我用的do while型的循环写的,果然节省了标签和码量,以后的题可以再试试。</span></p>
<p><span style="font-size: 15px">回文串:</span></p>
<p><span style="font-size: 15px">一维数组操作,比较简单,但题目提示中关于syscall中8和12的区别还是需要注意的:12是<span style="font-size: 16px"><strong>单字符读入</strong></span>,类似于getchar()(?),而8是<span style="font-size: 16px"><strong>一行读入</strong></span>,有点像fgets(),会把换行读进去,且需要预先设定到底最多读入多少个字符。几个判断函数需要好好熟悉一下,看看啥时候该用什么。一般for循环喜欢用beq,do while喜欢用bne</span></p>
<p><span style="font-size: 15px">卷积运算:</span></p>
<p><span style="font-size: 15px">弱化版的卷积运算,不需要填充,也不需要翻转,没有花里胡哨的操作,只要老老实实操作二维数组就行了。在下手之前一定要把地址计算和下标范围给解决了,只有数学上写的是对的,程序才有可能对。下面给出C++代码,注释部分是对于地址计算和下标的思考。</span></p>
<div class="cnblogs_code">
<pre><span style="color: rgba(0, 128, 128, 1)"> 1</span> #include &lt;bits/stdc++.h&gt;
<span style="color: rgba(0, 128, 128, 1)"> 2</span> <span style="color: rgba(0, 0, 255, 1)">int</span> ans[<span style="color: rgba(128, 0, 128, 1)">10</span>][<span style="color: rgba(128, 0, 128, 1)">10</span><span style="color: rgba(0, 0, 0, 1)">];
</span><span style="color: rgba(0, 128, 128, 1)"> 3</span> <span style="color: rgba(0, 0, 255, 1)">int</span><span style="color: rgba(0, 0, 0, 1)"> m1,n1,m2,n2;
</span><span style="color: rgba(0, 128, 128, 1)"> 4</span> <span style="color: rgba(0, 0, 255, 1)">int</span> core[<span style="color: rgba(128, 0, 128, 1)">10</span>][<span style="color: rgba(128, 0, 128, 1)">10</span>],matrix[<span style="color: rgba(128, 0, 128, 1)">10</span>][<span style="color: rgba(128, 0, 128, 1)">10</span><span style="color: rgba(0, 0, 0, 1)">];
</span><span style="color: rgba(0, 128, 128, 1)"> 5</span> <span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> Convolution();
</span><span style="color: rgba(0, 128, 128, 1)"> 6</span> <span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> print();
</span><span style="color: rgba(0, 128, 128, 1)"> 7</span> <span style="color: rgba(0, 0, 255, 1)">int</span><span style="color: rgba(0, 0, 0, 1)"> main() {
</span><span style="color: rgba(0, 128, 128, 1)"> 8</span>   scanf(<span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">%d %d %d %d</span><span style="color: rgba(128, 0, 0, 1)">"</span>,&amp;m1,&amp;n1,&amp;m2,&amp;<span style="color: rgba(0, 0, 0, 1)">n2);
</span><span style="color: rgba(0, 128, 128, 1)"> 9</span>   <span style="color: rgba(0, 0, 255, 1)">for</span>(<span style="color: rgba(0, 0, 255, 1)">int</span> i=<span style="color: rgba(128, 0, 128, 1)">0</span>;i&lt;m1;i++<span style="color: rgba(0, 0, 0, 1)">){
</span><span style="color: rgba(0, 128, 128, 1)">10</span>         <span style="color: rgba(0, 0, 255, 1)">for</span>(<span style="color: rgba(0, 0, 255, 1)">int</span> j=<span style="color: rgba(128, 0, 128, 1)">0</span>;j&lt;n1;j++<span style="color: rgba(0, 0, 0, 1)">){
</span><span style="color: rgba(0, 128, 128, 1)">11</span>             scanf(<span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">%d</span><span style="color: rgba(128, 0, 0, 1)">"</span>,&amp;<span style="color: rgba(0, 0, 0, 1)">matrix);
</span><span style="color: rgba(0, 128, 128, 1)">12</span> <span style="color: rgba(0, 0, 0, 1)">      }
</span><span style="color: rgba(0, 128, 128, 1)">13</span> <span style="color: rgba(0, 0, 0, 1)">    }
</span><span style="color: rgba(0, 128, 128, 1)">14</span>   <span style="color: rgba(0, 0, 255, 1)">for</span>(<span style="color: rgba(0, 0, 255, 1)">int</span> i=<span style="color: rgba(128, 0, 128, 1)">0</span>;i&lt;m2;i++<span style="color: rgba(0, 0, 0, 1)">){
</span><span style="color: rgba(0, 128, 128, 1)">15</span>         <span style="color: rgba(0, 0, 255, 1)">for</span>(<span style="color: rgba(0, 0, 255, 1)">int</span> j=<span style="color: rgba(128, 0, 128, 1)">0</span>;j&lt;n2;j++<span style="color: rgba(0, 0, 0, 1)">){
</span><span style="color: rgba(0, 128, 128, 1)">16</span>             scanf(<span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">%d</span><span style="color: rgba(128, 0, 0, 1)">"</span>,&amp;<span style="color: rgba(0, 0, 0, 1)">core);
</span><span style="color: rgba(0, 128, 128, 1)">17</span> <span style="color: rgba(0, 0, 0, 1)">      }
</span><span style="color: rgba(0, 128, 128, 1)">18</span> <span style="color: rgba(0, 0, 0, 1)">    }
</span><span style="color: rgba(0, 128, 128, 1)">19</span> <span style="color: rgba(0, 0, 0, 1)">    Convolution();
</span><span style="color: rgba(0, 128, 128, 1)">20</span> <span style="color: rgba(0, 0, 0, 1)">    print();
</span><span style="color: rgba(0, 128, 128, 1)">21</span>   <span style="color: rgba(0, 0, 255, 1)">return</span> <span style="color: rgba(128, 0, 128, 1)">0</span><span style="color: rgba(0, 0, 0, 1)">;
</span><span style="color: rgba(0, 128, 128, 1)">22</span> <span style="color: rgba(0, 0, 0, 1)">}
</span><span style="color: rgba(0, 128, 128, 1)">23</span> <span style="color: rgba(0, 128, 0, 1)">//</span><span style="color: rgba(0, 128, 0, 1)">本题不需要翻转,也不需要填充
</span><span style="color: rgba(0, 128, 128, 1)">24</span> <span style="color: rgba(0, 128, 0, 1)">//</span><span style="color: rgba(0, 128, 0, 1)">下面用变量i,j控制卷积核的移动,k,l作为数据运算时的卷积核中元素行列标号
</span><span style="color: rgba(0, 128, 128, 1)">25</span> <span style="color: rgba(0, 128, 0, 1)">//</span><span style="color: rgba(0, 128, 0, 1)">分析可知:0&lt;=i&lt;=m1-m2   0&lt;=j&lt;=n1-n2   
</span><span style="color: rgba(0, 128, 128, 1)">26</span> <span style="color: rgba(0, 128, 0, 1)">//</span><span style="color: rgba(0, 128, 0, 1)">分析可知:0&lt;=k&lt;m2       0&lt;=l&lt;n2   
</span><span style="color: rgba(0, 128, 128, 1)">27</span> <span style="color: rgba(0, 128, 0, 1)">//</span><span style="color: rgba(0, 128, 0, 1)">计算规则:ans+=core*matrix</span>
<span style="color: rgba(0, 128, 128, 1)">28</span> <span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> Convolution(){
</span><span style="color: rgba(0, 128, 128, 1)">29</span>   <span style="color: rgba(0, 0, 255, 1)">for</span>(<span style="color: rgba(0, 0, 255, 1)">int</span> i=<span style="color: rgba(128, 0, 128, 1)">0</span>;i&lt;=m1-m2;i++<span style="color: rgba(0, 0, 0, 1)">){
</span><span style="color: rgba(0, 128, 128, 1)">30</span>         <span style="color: rgba(0, 0, 255, 1)">for</span>(<span style="color: rgba(0, 0, 255, 1)">int</span> j=<span style="color: rgba(128, 0, 128, 1)">0</span>;j&lt;=n1-n2;j++<span style="color: rgba(0, 0, 0, 1)">){
</span><span style="color: rgba(0, 128, 128, 1)">31</span>             <span style="color: rgba(0, 0, 255, 1)">for</span>(<span style="color: rgba(0, 0, 255, 1)">int</span> k=<span style="color: rgba(128, 0, 128, 1)">0</span>;k&lt;m2;k++<span style="color: rgba(0, 0, 0, 1)">){
</span><span style="color: rgba(0, 128, 128, 1)">32</span>               <span style="color: rgba(0, 0, 255, 1)">for</span>(<span style="color: rgba(0, 0, 255, 1)">int</span> l=<span style="color: rgba(128, 0, 128, 1)">0</span>;l&lt;n2;l++<span style="color: rgba(0, 0, 0, 1)">){
</span><span style="color: rgba(0, 128, 128, 1)">33</span>                     ans+=core*matrix;
</span><span style="color: rgba(0, 128, 128, 1)">34</span> <span style="color: rgba(0, 0, 0, 1)">                }
</span><span style="color: rgba(0, 128, 128, 1)">35</span> <span style="color: rgba(0, 0, 0, 1)">            }
</span><span style="color: rgba(0, 128, 128, 1)">36</span> <span style="color: rgba(0, 0, 0, 1)">      }
</span><span style="color: rgba(0, 128, 128, 1)">37</span> <span style="color: rgba(0, 0, 0, 1)">    }
</span><span style="color: rgba(0, 128, 128, 1)">38</span> <span style="color: rgba(0, 0, 0, 1)">}
</span><span style="color: rgba(0, 128, 128, 1)">39</span> <span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> print(){
</span><span style="color: rgba(0, 128, 128, 1)">40</span>   <span style="color: rgba(0, 0, 255, 1)">for</span>(<span style="color: rgba(0, 0, 255, 1)">int</span> i=<span style="color: rgba(128, 0, 128, 1)">0</span>;i&lt;=m1-m2;i++<span style="color: rgba(0, 0, 0, 1)">){
</span><span style="color: rgba(0, 128, 128, 1)">41</span>         <span style="color: rgba(0, 0, 255, 1)">for</span>(<span style="color: rgba(0, 0, 255, 1)">int</span> j=<span style="color: rgba(128, 0, 128, 1)">0</span>;j&lt;=n1-n2;j++<span style="color: rgba(0, 0, 0, 1)">){
</span><span style="color: rgba(0, 128, 128, 1)">42</span>             printf(<span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">%d </span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(0, 0, 0, 1)">,ans);
</span><span style="color: rgba(0, 128, 128, 1)">43</span> <span style="color: rgba(0, 0, 0, 1)">      }
</span><span style="color: rgba(0, 128, 128, 1)">44</span>         printf(<span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">\n</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(0, 0, 0, 1)">);
</span><span style="color: rgba(0, 128, 128, 1)">45</span> <span style="color: rgba(0, 0, 0, 1)">    }
</span><span style="color: rgba(0, 128, 128, 1)">46</span> }</pre>
</div>
<p>&nbsp;</p>
<p><span style="font-size: 15px">本题我处理不好的地方:虽然一遍就过样例了,但是编写过程中还是出了一些问题:首先是<strong>滥用a0寄存器</strong>。这不是我的本意,我真的是用完了t和s,然后想暂时借用一下a0,结果写到最后发现需要输出字符的时候要覆盖掉a0的值,这样我就白忙活了。情急之下,我每次打印字符之前都先把a0拷贝一份,打印完字符之后再拷贝回来,做到了代码改动最少,但是看起来却特别的傻。如果没有意识到这一点,不知道会错成什么样子。第二个问题是a与s打混了,就是因为滥用a0,所以敲着敲着发现有个应该是s0的地方被写成了a0,as在键盘相邻,被打错的可能行还是有的。最后一个问题是mflo打错了,打成了mulo,结果还真有一个mulo,功能大概是考虑溢出的乘法,这个错误也是写着写着扫了一眼发现的,太低级的失误了。</span></p>
<p><span style="font-size: 15px">全排列:</span></p>
<p><span style="font-size: 15px">典型递归程序,<strong>也是P2考试的重点</strong>。如果不清楚递归程序写法的,请先在OJ上重新完成全排列问题以及汉诺塔问题。如果不太懂得如何用汇编实现递归程序,请仔细研读下面的汉诺塔汇编代码。以及如果做了哈密顿回路那道题,会发现这个题相当于哈密顿的弱化版(此题没有操作二维数组,所以比较好写一点)。在有了哈密顿的经验之后,操作栈变得更加熟练了。这个题我最开始的确是写了标记数组标记,之后<strong>在回溯的时候再消去标记</strong>,结果写着写着发现居然只写了注释,没写相应的代码。。发现只有一个输出之后竟然用了十几分钟才发现这里错了。测试debug用n=2或者3就够了,数据大了是给自己添麻烦。推荐过了这个题之后再做做哈密顿那道题,会比较顺利。纠正一个自己之前的迷惑点:之前以为31号寄存器每进入一个新的标签,都会自动改变一下,其实这是不对的。<strong>只有jal能改动31号寄存器的值</strong>(当时就是纠结这个才会哈密顿写了6小时,不过最后弄明白就很好了)</span></p>
<p><span style="font-size: 15px">另外感觉全排列比汉诺塔更适合在大一程设中当做例题讲,汉诺塔很容易把不明白函数传参的都搞晕了,而全排列只传递一个参数,不会卡在这里。不妨压一波P2课上测试考汉诺塔?可能不让输出路径只让输出方案数(推规律用通项公式水过去的统统问答时打死)课下有时间还是自己试试吧,竞赛+运动会完事儿了时间多的一匹,是补作业和肝计组的好时候了。去年好像还考了矩阵快速幂,也可以课下准备准备快速幂取模和矩阵快速幂,操作二维数组应该是比较常用且在考察范围内的知识点吧。</span></p>
<p><span style="font-size: 15px">P2之前一定要看一遍preview里的教程,不能再在问答环节尴尬了。</span></p>
<p><span style="font-size: 15px">01迷宫:</span></p>
<p><span style="font-size: 15px">这个题是二维数组+dfs的题目,是我考场上不敢碰的题(一道一个半小时,不加debug)递归终止条件是到终点。递归深入的条件是:某个方向走完之后没越界,且是0。每次深入之前,先把要到的那个位置在原来的矩阵中修改为1(即以后不可以走),然后再dfs,最后再把原来矩阵修改回去。注意<strong>起始点先标记上</strong>!</span></p>
<p><span style="font-size: 15px">可能遇到的困难:在做这道题之前,室友和我讨论了一下关于在递归中写多个if语句如何实现跳回去再调回来的功能,以保证所有的if都可以执行一次,我依托宏封装基本操作以方便编程,把判断条件单独放入一个标签judge,维护栈并用jal跳转至judge进行判断,最后jr跳回来正好是下一个if语句,解决了这个问题。光说可能不太清楚,下面提供一下汇编程序实现01迷宫,关注dfs,dfswork,judge,back四个标签</span><strong><span style="font-size: 16px">(仅供自己留备份+其他同学学习参考!严禁抄袭!提交一定会被查重)</span></strong></p>
<p>&nbsp;</p>
<div class="cnblogs_Highlighter">
<pre class="brush:cpp;gutter:true;">C++<br>#include &lt;iostream&gt;
#include &lt;bits/stdc++.h&gt;
int matrix;
int n,m,sx,sy,ex,ey;
int ans=0;
typedef struct {
        int dx;
        int dy;
}delta;
delta d={{0,-1},{0,1},{-1,0},{1,0}}; //高级语言中应该采取的走迷宫的写法
//在dfs中for(i=0;i&lt;4;i++){遍历方向}
void dfs(int x,int y);
int overflow(int x,int y,int dx,int dy);
int main() {
        scanf("%d %d",&amp;n,&amp;m);
        for(int i=1;i&lt;=n;i++){
                for(int j=1;j&lt;=m;j++){
                        scanf("%d",&amp;matrix);
                }
        }
        scanf("%d %d",&amp;sx,&amp;sy);
        scanf("%d %d",&amp;ex,&amp;ey);
        matrix=1;
        dfs(sx,sy);
        printf("%d\n",ans);
        return 0;
}
void dfs(int x,int y){
        if(x==ex &amp;&amp; y==ey){
                ans++;
                return;
        }//考虑到mips中多开数组或者用结构体在规定时间内编码难以接受,且为了翻译方便,所以没有用循环和方向数组
        //事实上应该声明一个方向结构体数组,存储下来所有方向,然后写一个循环跑所有方向,这样节省在高级语言中的代码量
        if(!overflow(x,y,0,-1) &amp;&amp; !matrix){
                matrix=1;
                dfs(x,y-1);
                matrix=0;
        }
        if(!overflow(x,y,0,1) &amp;&amp; !matrix){
                matrix=1;
                dfs(x,y+1);
                matrix=0;
        }
        if(!overflow(x,y,-1,0) &amp;&amp; !matrix){
                matrix=1;
                dfs(x-1,y);
                matrix=0;
        }
        if(!overflow(x,y,1,0) &amp;&amp; !matrix){
                matrix=1;
                dfs(x+1,y);
                matrix=0;
        }
}
int overflow(int x,int y,int dx,int dy){
        if(x+dx&lt;=n &amp;&amp; x+dx&gt;=1 &amp;&amp; y+dy&lt;=m &amp;&amp; y+dy&gt;=1)
                return 0;
        return 1;
}</pre>
</div>
<div class="cnblogs_code">
<pre><span style="color: rgba(0, 128, 128, 1)">1</span> <span style="color: rgba(0, 0, 0, 1)">.data
</span><span style="color: rgba(0, 128, 128, 1)">2</span> <span style="color: rgba(0, 128, 128, 1)">matrix:</span>    .space <span style="color: rgba(128, 0, 128, 1)">400</span>
<span style="color: rgba(0, 128, 128, 1)">3</span> <span style="color: rgba(0, 0, 0, 1)">.macro readint(%ans) #常用简单操作写成宏比较方便
</span><span style="color: rgba(0, 128, 128, 1)">4</span>   li    $v0,<span style="color: rgba(128, 0, 128, 1)">5</span>
<span style="color: rgba(0, 128, 128, 1)">5</span>   <span style="color: rgba(0, 0, 255, 1)">syscall</span>
<span style="color: rgba(0, 128, 128, 1)">6</span> <span style="color: rgba(0, 0, 0, 1)">    move    %ans,$v0
</span><span style="color: rgba(0, 128, 128, 1)">7</span> <span style="color: rgba(0, 0, 0, 1)">.end_macro
</span><span style="color: rgba(0, 128, 128, 1)">8</span> <span style="color: rgba(0, 0, 0, 1)">.macro save(%a)      #入栈
</span><span style="color: rgba(0, 128, 128, 1)">9</span> <span style="color: rgba(0, 0, 0, 1)">    sw    %a,($sp)
</span><span style="color: rgba(0, 128, 128, 1)"> 10</span>   addi    $sp,$sp,-<span style="color: rgba(128, 0, 128, 1)">4</span>
<span style="color: rgba(0, 128, 128, 1)"> 11</span> <span style="color: rgba(0, 0, 0, 1)">.end_macro
</span><span style="color: rgba(0, 128, 128, 1)"> 12</span> <span style="color: rgba(0, 0, 0, 1)">.macro load(%a)      #出栈
</span><span style="color: rgba(0, 128, 128, 1)"> 13</span>   addi    $sp,$sp,<span style="color: rgba(128, 0, 128, 1)">4</span>
<span style="color: rgba(0, 128, 128, 1)"> 14</span> <span style="color: rgba(0, 0, 0, 1)">    lw    %a,($sp)
</span><span style="color: rgba(0, 128, 128, 1)"> 15</span> <span style="color: rgba(0, 0, 0, 1)">.end_macro
</span><span style="color: rgba(0, 128, 128, 1)"> 16</span> <span style="color: rgba(0, 0, 0, 1)">.text
</span><span style="color: rgba(0, 128, 128, 1)"> 17</span> <span style="color: rgba(0, 0, 0, 1)">    readint($s0)      #s0是n
</span><span style="color: rgba(0, 128, 128, 1)"> 18</span> <span style="color: rgba(0, 0, 0, 1)">    readint($s1)      #s1是m
</span><span style="color: rgba(0, 128, 128, 1)"> 19</span>   li    $s7,<span style="color: rgba(128, 0, 128, 1)">0</span><span style="color: rgba(0, 0, 0, 1)">      #s7是方案数
</span><span style="color: rgba(0, 128, 128, 1)"> 20</span>   li    $t0,<span style="color: rgba(128, 0, 128, 1)">1</span><span style="color: rgba(0, 0, 0, 1)">      #t0是i
</span><span style="color: rgba(0, 128, 128, 1)"> 21</span> <span style="color: rgba(0, 128, 128, 1)">read_matrix:</span>
<span style="color: rgba(0, 128, 128, 1)"> 22</span> <span style="color: rgba(0, 0, 0, 1)">    bgt    $t0,$s0,read_matrix_end
</span><span style="color: rgba(0, 128, 128, 1)"> 23</span>   li    $t1,<span style="color: rgba(128, 0, 128, 1)">1</span>
<span style="color: rgba(0, 128, 128, 1)"> 24</span> <span style="color: rgba(0, 128, 128, 1)">read:</span>
<span style="color: rgba(0, 128, 128, 1)"> 25</span> <span style="color: rgba(0, 0, 0, 1)">    bgt    $t1,$s1,read_end
</span><span style="color: rgba(0, 128, 128, 1)"> 26</span>   addi    $t2,$t0,-<span style="color: rgba(128, 0, 128, 1)">1</span>
<span style="color: rgba(0, 128, 128, 1)"> 27</span> <span style="color: rgba(0, 0, 0, 1)">    mult    $t2,$s1
</span><span style="color: rgba(0, 128, 128, 1)"> 28</span>   mflo    $t2      #t2=(i-<span style="color: rgba(128, 0, 128, 1)">1</span><span style="color: rgba(0, 0, 0, 1)">)*m
</span><span style="color: rgba(0, 128, 128, 1)"> 29</span>   <span style="color: rgba(0, 0, 255, 1)">add</span>    $t2,$t2,$t1    #t2=(i-<span style="color: rgba(128, 0, 128, 1)">1</span><span style="color: rgba(0, 0, 0, 1)">)*m+j
</span><span style="color: rgba(0, 128, 128, 1)"> 30</span>   sll    $t2,$t2,<span style="color: rgba(128, 0, 128, 1)">2</span>
<span style="color: rgba(0, 128, 128, 1)"> 31</span> <span style="color: rgba(0, 0, 0, 1)">    la    $s2,matrix
</span><span style="color: rgba(0, 128, 128, 1)"> 32</span>   <span style="color: rgba(0, 0, 255, 1)">add</span><span style="color: rgba(0, 0, 0, 1)">    $t2,$s2,$t2    #t2是在矩阵中的位置
</span><span style="color: rgba(0, 128, 128, 1)"> 33</span>   li    $v0,<span style="color: rgba(128, 0, 128, 1)">5</span>
<span style="color: rgba(0, 128, 128, 1)"> 34</span>   <span style="color: rgba(0, 0, 255, 1)">syscall</span>   
<span style="color: rgba(0, 128, 128, 1)"> 35</span> <span style="color: rgba(0, 0, 0, 1)">    sw    $v0,($t2)    #数据存储进入矩阵
</span><span style="color: rgba(0, 128, 128, 1)"> 36</span>   addi    $t1,$t1,<span style="color: rgba(128, 0, 128, 1)">1</span>
<span style="color: rgba(0, 128, 128, 1)"> 37</span> <span style="color: rgba(0, 0, 0, 1)">    j    read
</span><span style="color: rgba(0, 128, 128, 1)"> 38</span> <span style="color: rgba(0, 128, 128, 1)">read_end:</span>
<span style="color: rgba(0, 128, 128, 1)"> 39</span>   addi    $t0,$t0,<span style="color: rgba(128, 0, 128, 1)">1</span>
<span style="color: rgba(0, 128, 128, 1)"> 40</span> <span style="color: rgba(0, 0, 0, 1)">    j    read_matrix
</span><span style="color: rgba(0, 128, 128, 1)"> 41</span> <span style="color: rgba(0, 128, 128, 1)">read_matrix_end:</span>
<span style="color: rgba(0, 128, 128, 1)"> 42</span> <span style="color: rgba(0, 0, 0, 1)">    readint($s2)      #s2,s3,s4,s5分别是起始行列,终点行列
</span><span style="color: rgba(0, 128, 128, 1)"> 43</span> <span style="color: rgba(0, 0, 0, 1)">    readint($s3)
</span><span style="color: rgba(0, 128, 128, 1)"> 44</span> <span style="color: rgba(0, 0, 0, 1)">    readint($s4)
</span><span style="color: rgba(0, 128, 128, 1)"> 45</span> <span style="color: rgba(0, 0, 0, 1)">    readint($s5)
</span><span style="color: rgba(0, 128, 128, 1)"> 46</span>   
<span style="color: rgba(0, 128, 128, 1)"> 47</span>   addi    $t0,$s2,-<span style="color: rgba(128, 0, 128, 1)">1</span>
<span style="color: rgba(0, 128, 128, 1)"> 48</span> <span style="color: rgba(0, 0, 0, 1)">    mult    $t0,$s1
</span><span style="color: rgba(0, 128, 128, 1)"> 49</span> <span style="color: rgba(0, 0, 0, 1)">    mflo    $t0
</span><span style="color: rgba(0, 128, 128, 1)"> 50</span>   <span style="color: rgba(0, 0, 255, 1)">add</span><span style="color: rgba(0, 0, 0, 1)">    $t0,$t0,$s3
</span><span style="color: rgba(0, 128, 128, 1)"> 51</span>   sll    $t0,$t0,<span style="color: rgba(128, 0, 128, 1)">2</span>
<span style="color: rgba(0, 128, 128, 1)"> 52</span> <span style="color: rgba(0, 0, 0, 1)">    la    $t1,matrix
</span><span style="color: rgba(0, 128, 128, 1)"> 53</span>   <span style="color: rgba(0, 0, 255, 1)">add</span><span style="color: rgba(0, 0, 0, 1)">    $t0,$t0,$t1
</span><span style="color: rgba(0, 128, 128, 1)"> 54</span>   li    $t2,<span style="color: rgba(128, 0, 128, 1)">1</span>
<span style="color: rgba(0, 128, 128, 1)"> 55</span> <span style="color: rgba(0, 0, 0, 1)">    sw    $t2,($t0)    #把出发点的位置标记为1,然后再dfs(最开始忘了,所以最终得到的方案数比预计的多)
</span><span style="color: rgba(0, 128, 128, 1)"> 56</span>   
<span style="color: rgba(0, 128, 128, 1)"> 57</span> <span style="color: rgba(0, 0, 0, 1)">    move    $a0,$s2
</span><span style="color: rgba(0, 128, 128, 1)"> 58</span> <span style="color: rgba(0, 0, 0, 1)">    move    $a1,$s3      #dfs参数,即目前的行和列
</span><span style="color: rgba(0, 128, 128, 1)"> 59</span> <span style="color: rgba(0, 0, 0, 1)">    jal    dfs   
</span><span style="color: rgba(0, 128, 128, 1)"> 60</span>   
<span style="color: rgba(0, 128, 128, 1)"> 61</span>   li    $v0,<span style="color: rgba(128, 0, 128, 1)">1</span>
<span style="color: rgba(0, 128, 128, 1)"> 62</span> <span style="color: rgba(0, 0, 0, 1)">    move    $a0,$s7
</span><span style="color: rgba(0, 128, 128, 1)"> 63</span>   <span style="color: rgba(0, 0, 255, 1)">syscall</span>
<span style="color: rgba(0, 128, 128, 1)"> 64</span>   li    $v0,<span style="color: rgba(128, 0, 128, 1)">10</span>
<span style="color: rgba(0, 128, 128, 1)"> 65</span>   <span style="color: rgba(0, 0, 255, 1)">syscall</span>
<span style="color: rgba(0, 128, 128, 1)"> 66</span>   
<span style="color: rgba(0, 128, 128, 1)"> 67</span>   
<span style="color: rgba(0, 128, 128, 1)"> 68</span> <span style="color: rgba(0, 128, 128, 1)">dfs:</span><span style="color: rgba(0, 0, 0, 1)">                #dfs写的是返回条件,dfswork里面才写了递归调用      
</span><span style="color: rgba(0, 128, 128, 1)"> 69</span> <span style="color: rgba(0, 0, 0, 1)">    beq    $a0,$s4,hope
</span><span style="color: rgba(0, 128, 128, 1)"> 70</span> <span style="color: rgba(0, 0, 0, 1)">    j    dfswork
</span><span style="color: rgba(0, 128, 128, 1)"> 71</span> <span style="color: rgba(0, 128, 128, 1)">hope:</span>
<span style="color: rgba(0, 128, 128, 1)"> 72</span> <span style="color: rgba(0, 0, 0, 1)">    beq    $a1,$s5,ansadd
</span><span style="color: rgba(0, 128, 128, 1)"> 73</span> <span style="color: rgba(0, 0, 0, 1)">    j    dfswork
</span><span style="color: rgba(0, 128, 128, 1)"> 74</span> <span style="color: rgba(0, 128, 128, 1)">ansadd:</span>
<span style="color: rgba(0, 128, 128, 1)"> 75</span>   addi    $s7,$s7,<span style="color: rgba(128, 0, 128, 1)">1</span>
<span style="color: rgba(0, 128, 128, 1)"> 76</span>   jr    $<span style="color: rgba(128, 0, 128, 1)">31</span>
<span style="color: rgba(0, 128, 128, 1)"> 77</span>   
<span style="color: rgba(0, 128, 128, 1)"> 78</span> #<span style="color: rgba(0, 128, 128, 1)">多个if语句的跳转的一种写法:</span><span style="color: rgba(0, 0, 0, 1)">为了能让多个if语句都能执行,并不能直接使用beq等指令,一种实现方法是用jal连接下一步并跳转到一个专门用于判断的过程judge中去
</span><span style="color: rgba(0, 128, 128, 1)"> 79</span> <span style="color: rgba(0, 0, 0, 1)">#由于jal跳转,所以需要维护栈,如果用宏来封装维护栈的过程的话,这里就特别容易写(推荐把读入数据,维护栈这种常用简单操作封装,至于其他用到额外寄存器的操作,请谨慎封装)
</span><span style="color: rgba(0, 128, 128, 1)"> 80</span> <span style="color: rgba(0, 128, 128, 1)">dfswork:</span>               
<span style="color: rgba(0, 128, 128, 1)"> 81</span> <span style="color: rgba(0, 0, 0, 1)">    save($a0)
</span><span style="color: rgba(0, 128, 128, 1)"> 82</span> <span style="color: rgba(0, 0, 0, 1)">    save($a1)
</span><span style="color: rgba(0, 128, 128, 1)"> 83</span>   save($<span style="color: rgba(128, 0, 128, 1)">31</span><span style="color: rgba(0, 0, 0, 1)">)      #第一次进时,这里存的是回主函数的地址
</span><span style="color: rgba(0, 128, 128, 1)"> 84</span>   addi    $a0,$a0,<span style="color: rgba(128, 0, 128, 1)">0</span>
<span style="color: rgba(0, 128, 128, 1)"> 85</span>   addi    $a1,$a1,-<span style="color: rgba(128, 0, 128, 1)">1</span>
<span style="color: rgba(0, 128, 128, 1)"> 86</span> <span style="color: rgba(0, 0, 0, 1)">    jal    judge
</span><span style="color: rgba(0, 128, 128, 1)"> 87</span>   load($<span style="color: rgba(128, 0, 128, 1)">31</span><span style="color: rgba(0, 0, 0, 1)">)
</span><span style="color: rgba(0, 128, 128, 1)"> 88</span> <span style="color: rgba(0, 0, 0, 1)">    load($a1)
</span><span style="color: rgba(0, 128, 128, 1)"> 89</span> <span style="color: rgba(0, 0, 0, 1)">    load($a0)         #完成对于一个方向的判断
</span><span style="color: rgba(0, 128, 128, 1)"> 90</span>   
<span style="color: rgba(0, 128, 128, 1)"> 91</span> <span style="color: rgba(0, 0, 0, 1)">    save($a0)
</span><span style="color: rgba(0, 128, 128, 1)"> 92</span> <span style="color: rgba(0, 0, 0, 1)">    save($a1)
</span><span style="color: rgba(0, 128, 128, 1)"> 93</span>   save($<span style="color: rgba(128, 0, 128, 1)">31</span><span style="color: rgba(0, 0, 0, 1)">)
</span><span style="color: rgba(0, 128, 128, 1)"> 94</span>   addi    $a0,$a0,<span style="color: rgba(128, 0, 128, 1)">0</span>
<span style="color: rgba(0, 128, 128, 1)"> 95</span>   addi    $a1,$a1,<span style="color: rgba(128, 0, 128, 1)">1</span>
<span style="color: rgba(0, 128, 128, 1)"> 96</span> <span style="color: rgba(0, 0, 0, 1)">    jal    judge
</span><span style="color: rgba(0, 128, 128, 1)"> 97</span>   load($<span style="color: rgba(128, 0, 128, 1)">31</span><span style="color: rgba(0, 0, 0, 1)">)
</span><span style="color: rgba(0, 128, 128, 1)"> 98</span> <span style="color: rgba(0, 0, 0, 1)">    load($a1)
</span><span style="color: rgba(0, 128, 128, 1)"> 99</span> <span style="color: rgba(0, 0, 0, 1)">    load($a0)
</span><span style="color: rgba(0, 128, 128, 1)">100</span>   
<span style="color: rgba(0, 128, 128, 1)">101</span> <span style="color: rgba(0, 0, 0, 1)">    save($a0)
</span><span style="color: rgba(0, 128, 128, 1)">102</span> <span style="color: rgba(0, 0, 0, 1)">    save($a1)
</span><span style="color: rgba(0, 128, 128, 1)">103</span>   save($<span style="color: rgba(128, 0, 128, 1)">31</span><span style="color: rgba(0, 0, 0, 1)">)
</span><span style="color: rgba(0, 128, 128, 1)">104</span>   addi    $a0,$a0,-<span style="color: rgba(128, 0, 128, 1)">1</span>
<span style="color: rgba(0, 128, 128, 1)">105</span>   addi    $a1,$a1,<span style="color: rgba(128, 0, 128, 1)">0</span>
<span style="color: rgba(0, 128, 128, 1)">106</span> <span style="color: rgba(0, 0, 0, 1)">    jal    judge
</span><span style="color: rgba(0, 128, 128, 1)">107</span>   load($<span style="color: rgba(128, 0, 128, 1)">31</span><span style="color: rgba(0, 0, 0, 1)">)
</span><span style="color: rgba(0, 128, 128, 1)">108</span> <span style="color: rgba(0, 0, 0, 1)">    load($a1)
</span><span style="color: rgba(0, 128, 128, 1)">109</span> <span style="color: rgba(0, 0, 0, 1)">    load($a0)
</span><span style="color: rgba(0, 128, 128, 1)">110</span>   
<span style="color: rgba(0, 128, 128, 1)">111</span> <span style="color: rgba(0, 0, 0, 1)">    save($a0)
</span><span style="color: rgba(0, 128, 128, 1)">112</span> <span style="color: rgba(0, 0, 0, 1)">    save($a1)
</span><span style="color: rgba(0, 128, 128, 1)">113</span>   save($<span style="color: rgba(128, 0, 128, 1)">31</span><span style="color: rgba(0, 0, 0, 1)">)
</span><span style="color: rgba(0, 128, 128, 1)">114</span>   addi    $a0,$a0,<span style="color: rgba(128, 0, 128, 1)">1</span>
<span style="color: rgba(0, 128, 128, 1)">115</span>   addi    $a1,$a1,<span style="color: rgba(128, 0, 128, 1)">0</span>
<span style="color: rgba(0, 128, 128, 1)">116</span> <span style="color: rgba(0, 0, 0, 1)">    jal    judge
</span><span style="color: rgba(0, 128, 128, 1)">117</span>   load($<span style="color: rgba(128, 0, 128, 1)">31</span><span style="color: rgba(0, 0, 0, 1)">)
</span><span style="color: rgba(0, 128, 128, 1)">118</span> <span style="color: rgba(0, 0, 0, 1)">    load($a1)
</span><span style="color: rgba(0, 128, 128, 1)">119</span> <span style="color: rgba(0, 0, 0, 1)">    load($a0)
</span><span style="color: rgba(0, 128, 128, 1)">120</span>   
<span style="color: rgba(0, 128, 128, 1)">121</span>   jr    $<span style="color: rgba(128, 0, 128, 1)">31</span><span style="color: rgba(0, 0, 0, 1)">      #返回上一个dfs
</span><span style="color: rgba(0, 128, 128, 1)">122</span>   
<span style="color: rgba(0, 128, 128, 1)">123</span> <span style="color: rgba(0, 128, 128, 1)">judge:</span>
<span style="color: rgba(0, 128, 128, 1)">124</span> <span style="color: rgba(0, 0, 0, 1)">    bgt    $a0,$s0,back    #如果行严格大于行数,返回
</span><span style="color: rgba(0, 128, 128, 1)">125</span>   ble    $a0,$<span style="color: rgba(128, 0, 128, 1)">0</span><span style="color: rgba(0, 0, 0, 1)">,back    #如果行号小于等于0,返回
</span><span style="color: rgba(0, 128, 128, 1)">126</span> <span style="color: rgba(0, 0, 0, 1)">    bgt    $a1,$s1,back    #同理
</span><span style="color: rgba(0, 128, 128, 1)">127</span>   ble    $a1,$<span style="color: rgba(128, 0, 128, 1)">0</span><span style="color: rgba(0, 0, 0, 1)">,back
</span><span style="color: rgba(0, 128, 128, 1)">128</span>   addi    $t0,$a0,-<span style="color: rgba(128, 0, 128, 1)">1</span><span style="color: rgba(0, 0, 0, 1)">    #由于存的时候就是这样的,所以此处也先减一
</span><span style="color: rgba(0, 128, 128, 1)">129</span> <span style="color: rgba(0, 0, 0, 1)">    mult    $t0,$s1
</span><span style="color: rgba(0, 128, 128, 1)">130</span> <span style="color: rgba(0, 0, 0, 1)">    mflo    $t1
</span><span style="color: rgba(0, 128, 128, 1)">131</span>   <span style="color: rgba(0, 0, 255, 1)">add</span><span style="color: rgba(0, 0, 0, 1)">    $t1,$t1,$a1
</span><span style="color: rgba(0, 128, 128, 1)">132</span>   sll    $t1,$t1,<span style="color: rgba(128, 0, 128, 1)">2</span>
<span style="color: rgba(0, 128, 128, 1)">133</span> <span style="color: rgba(0, 0, 0, 1)">    la    $t2,matrix
</span><span style="color: rgba(0, 128, 128, 1)">134</span>   <span style="color: rgba(0, 0, 255, 1)">add</span><span style="color: rgba(0, 0, 0, 1)">    $t1,$t1,$t2   
</span><span style="color: rgba(0, 128, 128, 1)">135</span> <span style="color: rgba(0, 0, 0, 1)">    lw    $t3,($t1)    #t3是矩阵中该位置的值,表示是否能走
</span><span style="color: rgba(0, 128, 128, 1)">136</span>   bne    $t3,$<span style="color: rgba(128, 0, 128, 1)">0</span><span style="color: rgba(0, 0, 0, 1)">,back    #如果t3不能走,回退一次
</span><span style="color: rgba(0, 128, 128, 1)">137</span>   li    $t4,<span style="color: rgba(128, 0, 128, 1)">1</span>
<span style="color: rgba(0, 128, 128, 1)">138</span> <span style="color: rgba(0, 0, 0, 1)">    sw    $t4,($t1)    #标记为不能走了
</span><span style="color: rgba(0, 128, 128, 1)">139</span>   save($<span style="color: rgba(128, 0, 128, 1)">31</span><span style="color: rgba(0, 0, 0, 1)">)      #第一次进时,这里存的是judge下一条的地址
</span><span style="color: rgba(0, 128, 128, 1)">140</span> <span style="color: rgba(0, 0, 0, 1)">    save($t1)
</span><span style="color: rgba(0, 128, 128, 1)">141</span> <span style="color: rgba(0, 0, 0, 1)">    save($t2)
</span><span style="color: rgba(0, 128, 128, 1)">142</span> <span style="color: rgba(0, 0, 0, 1)">    save($t3)
</span><span style="color: rgba(0, 128, 128, 1)">143</span> <span style="color: rgba(0, 0, 0, 1)">    save($t4)      #不管哪些需要存哪些不需要存了,xjb存就完事了(其实这里只需要$t1存起来),最开始我$t1忘了存了
</span><span style="color: rgba(0, 128, 128, 1)">144</span> <span style="color: rgba(0, 0, 0, 1)">    jal    dfs
</span><span style="color: rgba(0, 128, 128, 1)">145</span> <span style="color: rgba(0, 0, 0, 1)">    load($t4)
</span><span style="color: rgba(0, 128, 128, 1)">146</span> <span style="color: rgba(0, 0, 0, 1)">    load($t3)
</span><span style="color: rgba(0, 128, 128, 1)">147</span> <span style="color: rgba(0, 0, 0, 1)">    load($t2)
</span><span style="color: rgba(0, 128, 128, 1)">148</span> <span style="color: rgba(0, 0, 0, 1)">    load($t1)
</span><span style="color: rgba(0, 128, 128, 1)">149</span>   load($<span style="color: rgba(128, 0, 128, 1)">31</span><span style="color: rgba(0, 0, 0, 1)">)
</span><span style="color: rgba(0, 128, 128, 1)">150</span>   sw    $<span style="color: rgba(128, 0, 128, 1)">0</span><span style="color: rgba(0, 0, 0, 1)">,($t1)      #把值修改回去,以后又可以走了
</span><span style="color: rgba(0, 128, 128, 1)">151</span>   jr    $<span style="color: rgba(128, 0, 128, 1)">31</span><span style="color: rgba(0, 0, 0, 1)">      #回judge的下一条指令,即判断另一个方向
</span><span style="color: rgba(0, 128, 128, 1)">152</span>   
<span style="color: rgba(0, 128, 128, 1)">153</span>   
<span style="color: rgba(0, 128, 128, 1)">154</span> <span style="color: rgba(0, 128, 128, 1)">back:</span>
<span style="color: rgba(0, 128, 128, 1)">155</span>   jr    $<span style="color: rgba(128, 0, 128, 1)">31</span></pre>
</div>
<p>&nbsp;</p>
<p>&nbsp;</p>
<p>补充题:</p>
<p>选择排序:</p>
<p>当时没照着视频写,现在拿出来写了一下,发现没必要像教程中一样弄个global main(也不让用),直接写即可。因为怕错+自己太弱,所以先写了C代码,然后翻译的。比视频中写的短,不到70行。当然,有一定的规矩终究是好的,但从助教口中得知,就P2的难度来说,倒没必要这么搞。</p>
<p>矩阵快速幂:</p>
<p>先放出C++代码,注意取模取多了也会变慢而超时。////更新:快速幂的汇编代码考前更新不出来了,只是又写了一遍C的代码,保证如果碰到的话能快速写出正确代码,并做好了测试数据。</p>
<div class="cnblogs_code">
<pre><span style="color: rgba(0, 0, 0, 1)">#include </span>&lt;bits/stdc++.h&gt;
<span style="color: rgba(0, 0, 255, 1)">#define</span> ll    long long
<span style="color: rgba(0, 128, 0, 1)">//</span><span style="color: rgba(0, 128, 0, 1)">矩阵快速幂的快速之处不在于加速两个矩阵相乘时内部的计算速度
</span><span style="color: rgba(0, 128, 0, 1)">//</span><span style="color: rgba(0, 128, 0, 1)">而是减少矩阵之间做乘法的次数 </span>
ll mod=<span style="color: rgba(128, 0, 128, 1)">1000000007</span><span style="color: rgba(0, 0, 0, 1)">;
typedef </span><span style="color: rgba(0, 0, 255, 1)">struct</span><span style="color: rgba(0, 0, 0, 1)">{
    ll    a[</span><span style="color: rgba(128, 0, 128, 1)">200</span>][<span style="color: rgba(128, 0, 128, 1)">200</span><span style="color: rgba(0, 0, 0, 1)">];
}Matrix;
Matrix m,ans;
</span><span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> power(ll n,ll k);
Matrix mult(Matrix ans,Matrix </span><span style="color: rgba(0, 0, 255, 1)">base</span><span style="color: rgba(0, 0, 0, 1)">,ll n);
</span><span style="color: rgba(0, 0, 255, 1)">int</span><span style="color: rgba(0, 0, 0, 1)"> main() {
    ll n,k;
    scanf(</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">%lld %lld</span><span style="color: rgba(128, 0, 0, 1)">"</span>,&amp;n,&amp;<span style="color: rgba(0, 0, 0, 1)">k);
    </span><span style="color: rgba(0, 0, 255, 1)">for</span>(ll i=<span style="color: rgba(128, 0, 128, 1)">0</span>;i&lt;n;i++<span style="color: rgba(0, 0, 0, 1)">){
      </span><span style="color: rgba(0, 0, 255, 1)">for</span>(ll j=<span style="color: rgba(128, 0, 128, 1)">0</span>;j&lt;n;j++<span style="color: rgba(0, 0, 0, 1)">){
            scanf(</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">%lld</span><span style="color: rgba(128, 0, 0, 1)">"</span>,&amp;<span style="color: rgba(0, 0, 0, 1)">m.a);
      }
    }
    power(n,k);
    </span><span style="color: rgba(0, 0, 255, 1)">for</span>(ll i=<span style="color: rgba(128, 0, 128, 1)">0</span>;i&lt;n;i++<span style="color: rgba(0, 0, 0, 1)">){
      </span><span style="color: rgba(0, 0, 255, 1)">for</span>(ll j=<span style="color: rgba(128, 0, 128, 1)">0</span>;j&lt;n;j++<span style="color: rgba(0, 0, 0, 1)">){
            printf(</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">%lld </span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(0, 0, 0, 1)">,ans.a);
      }
      printf(</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">\n</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(0, 0, 0, 1)">);
    }
    </span><span style="color: rgba(0, 0, 255, 1)">return</span> <span style="color: rgba(128, 0, 128, 1)">0</span><span style="color: rgba(0, 0, 0, 1)">;
}
</span><span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> power(ll n,ll k){
    Matrix </span><span style="color: rgba(0, 0, 255, 1)">base</span>=<span style="color: rgba(0, 0, 0, 1)">m;
    </span><span style="color: rgba(0, 0, 255, 1)">for</span>(ll i=<span style="color: rgba(128, 0, 128, 1)">0</span>;i&lt;n;i++<span style="color: rgba(0, 0, 0, 1)">){
      ans.a</span>=<span style="color: rgba(128, 0, 128, 1)">1</span>; <span style="color: rgba(0, 128, 0, 1)">//</span><span style="color: rgba(0, 128, 0, 1)">构造单位矩阵 </span>
<span style="color: rgba(0, 0, 0, 1)">    }
    </span><span style="color: rgba(0, 0, 255, 1)">while</span>(k&gt;<span style="color: rgba(128, 0, 128, 1)">0</span><span style="color: rgba(0, 0, 0, 1)">){
      </span><span style="color: rgba(0, 0, 255, 1)">if</span>(k&amp;<span style="color: rgba(128, 0, 128, 1)">1</span><span style="color: rgba(0, 0, 0, 1)">){
            ans</span>=mult(ans,<span style="color: rgba(0, 0, 255, 1)">base</span><span style="color: rgba(0, 0, 0, 1)">,n);
      }
      </span><span style="color: rgba(0, 0, 255, 1)">base</span>=mult(<span style="color: rgba(0, 0, 255, 1)">base</span>,<span style="color: rgba(0, 0, 255, 1)">base</span><span style="color: rgba(0, 0, 0, 1)">,n);
      k</span>&gt;&gt;=<span style="color: rgba(128, 0, 128, 1)">1</span><span style="color: rgba(0, 0, 0, 1)">;
    }
}
Matrix mult(Matrix ans,Matrix </span><span style="color: rgba(0, 0, 255, 1)">base</span><span style="color: rgba(0, 0, 0, 1)">,ll n){
    Matrix result;
    </span><span style="color: rgba(0, 0, 255, 1)">for</span>(ll i=<span style="color: rgba(128, 0, 128, 1)">0</span>;i&lt;n;i++<span style="color: rgba(0, 0, 0, 1)">){
      </span><span style="color: rgba(0, 0, 255, 1)">for</span>(ll j=<span style="color: rgba(128, 0, 128, 1)">0</span>;j&lt;n;j++<span style="color: rgba(0, 0, 0, 1)">){
            result.a</span>=<span style="color: rgba(128, 0, 128, 1)">0</span><span style="color: rgba(0, 0, 0, 1)">;
      }
    }
    </span><span style="color: rgba(0, 0, 255, 1)">for</span>(ll i=<span style="color: rgba(128, 0, 128, 1)">0</span>;i&lt;n;i++<span style="color: rgba(0, 0, 0, 1)">){
      </span><span style="color: rgba(0, 0, 255, 1)">for</span>(ll j=<span style="color: rgba(128, 0, 128, 1)">0</span>;j&lt;n;j++<span style="color: rgba(0, 0, 0, 1)">){
            </span><span style="color: rgba(0, 0, 255, 1)">for</span>(ll k=<span style="color: rgba(128, 0, 128, 1)">0</span>;k&lt;n;k++<span style="color: rgba(0, 0, 0, 1)">){
                result.a</span>+=(((ans.a)*(<span style="color: rgba(0, 0, 255, 1)">base</span>.a))%<span style="color: rgba(0, 0, 0, 1)">mod);
</span><span style="color: rgba(0, 128, 0, 1)">//</span><span style="color: rgba(0, 128, 0, 1)">            result.a+=((ans.a%mod)*(base.a%mod)%mod);会慢,超时 </span>
                result.a%=<span style="color: rgba(0, 0, 0, 1)">mod;
            }
      }
    }
    </span><span style="color: rgba(0, 0, 255, 1)">return</span><span style="color: rgba(0, 0, 0, 1)"> result;
}</span></pre>
</div>
<p>&nbsp;</p>
<p>汉诺塔:</p>
<p>理解用汇编语言写递归的本质:把所有的参数都存在堆栈里,然后进下一层,最后递归终止时输出一行移动盘子。参考的去年OJ上的输出要求。</p>
<div class="cnblogs_code">
<pre>#include &lt;stdio.h&gt;<span style="color: rgba(0, 0, 0, 1)">
#include </span>&lt;stdlib.h&gt;
<span style="color: rgba(0, 0, 255, 1)">void</span> dfs(<span style="color: rgba(0, 0, 255, 1)">int</span> n,<span style="color: rgba(0, 0, 255, 1)">char</span> <span style="color: rgba(0, 0, 255, 1)">from</span>,<span style="color: rgba(0, 0, 255, 1)">char</span> tmp,<span style="color: rgba(0, 0, 255, 1)">char</span><span style="color: rgba(0, 0, 0, 1)"> to);
</span><span style="color: rgba(0, 0, 255, 1)">int</span><span style="color: rgba(0, 0, 0, 1)"> main() {
    </span><span style="color: rgba(0, 0, 255, 1)">int</span><span style="color: rgba(0, 0, 0, 1)"> n;
    </span><span style="color: rgba(0, 0, 255, 1)">char</span> <span style="color: rgba(0, 0, 255, 1)">from</span>=<span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">A</span><span style="color: rgba(128, 0, 0, 1)">'</span>,tmp=<span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">B</span><span style="color: rgba(128, 0, 0, 1)">'</span>,to=<span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(128, 0, 0, 1)">C</span><span style="color: rgba(128, 0, 0, 1)">'</span><span style="color: rgba(0, 0, 0, 1)">;
    scanf(</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">%d</span><span style="color: rgba(128, 0, 0, 1)">"</span>,&amp;<span style="color: rgba(0, 0, 0, 1)">n);
    dfs(n,</span><span style="color: rgba(0, 0, 255, 1)">from</span><span style="color: rgba(0, 0, 0, 1)">,tmp,to);
   
    </span><span style="color: rgba(0, 0, 255, 1)">return</span> <span style="color: rgba(128, 0, 128, 1)">0</span><span style="color: rgba(0, 0, 0, 1)">;
}
</span><span style="color: rgba(0, 0, 255, 1)">void</span> dfs(<span style="color: rgba(0, 0, 255, 1)">int</span> n,<span style="color: rgba(0, 0, 255, 1)">char</span> <span style="color: rgba(0, 0, 255, 1)">from</span>,<span style="color: rgba(0, 0, 255, 1)">char</span> tmp,<span style="color: rgba(0, 0, 255, 1)">char</span><span style="color: rgba(0, 0, 0, 1)"> to){
    </span><span style="color: rgba(0, 0, 255, 1)">if</span>(n==<span style="color: rgba(128, 0, 128, 1)">1</span><span style="color: rgba(0, 0, 0, 1)">){
      printf(</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">%c --&gt; %c\n</span><span style="color: rgba(128, 0, 0, 1)">"</span>,<span style="color: rgba(0, 0, 255, 1)">from</span><span style="color: rgba(0, 0, 0, 1)">,to);
      </span><span style="color: rgba(0, 0, 255, 1)">return</span><span style="color: rgba(0, 0, 0, 1)">;
    }
    dfs(n</span>-<span style="color: rgba(128, 0, 128, 1)">1</span>,<span style="color: rgba(0, 0, 255, 1)">from</span><span style="color: rgba(0, 0, 0, 1)">,to,tmp);
    dfs(</span><span style="color: rgba(128, 0, 128, 1)">1</span>,<span style="color: rgba(0, 0, 255, 1)">from</span><span style="color: rgba(0, 0, 0, 1)">,tmp,to);
    dfs(n</span>-<span style="color: rgba(128, 0, 128, 1)">1</span>,tmp,<span style="color: rgba(0, 0, 255, 1)">from</span><span style="color: rgba(0, 0, 0, 1)">,to);
    </span><span style="color: rgba(0, 0, 255, 1)">return</span><span style="color: rgba(0, 0, 0, 1)">;
}</span></pre>
</div>
<p>下面是递归程序,比较容易写</p>
<div class="cnblogs_code">
<pre><span style="color: rgba(0, 128, 128, 1)"> 1</span> <span style="color: rgba(0, 0, 0, 1)">.data
</span><span style="color: rgba(0, 128, 128, 1)"> 2</span> <span style="color: rgba(0, 128, 128, 1)">connect:</span>    .asciiz <span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)"> --&gt; </span><span style="color: rgba(128, 0, 0, 1)">"</span>
<span style="color: rgba(0, 128, 128, 1)"> 3</span> <span style="color: rgba(0, 0, 255, 1)">enter</span>:    .asciiz <span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">\n</span><span style="color: rgba(128, 0, 0, 1)">"</span>
<span style="color: rgba(0, 128, 128, 1)"> 4</span> <span style="color: rgba(0, 128, 128, 1)">_a:</span>    .asciiz <span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">A</span><span style="color: rgba(128, 0, 0, 1)">"</span>
<span style="color: rgba(0, 128, 128, 1)"> 5</span> <span style="color: rgba(0, 128, 128, 1)">_b:</span>    .asciiz <span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">B</span><span style="color: rgba(128, 0, 0, 1)">"</span>
<span style="color: rgba(0, 128, 128, 1)"> 6</span> <span style="color: rgba(0, 128, 128, 1)">_c:</span>    .asciiz <span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">C</span><span style="color: rgba(128, 0, 0, 1)">"</span>
<span style="color: rgba(0, 128, 128, 1)"> 7</span> <span style="color: rgba(0, 0, 0, 1)">.macro save(%a)
</span><span style="color: rgba(0, 128, 128, 1)"> 8</span> <span style="color: rgba(0, 0, 0, 1)">    sw    %a,($sp)
</span><span style="color: rgba(0, 128, 128, 1)"> 9</span>   addi    $sp,$sp,-<span style="color: rgba(128, 0, 128, 1)">4</span>
<span style="color: rgba(0, 128, 128, 1)">10</span> <span style="color: rgba(0, 0, 0, 1)">.end_macro
</span><span style="color: rgba(0, 128, 128, 1)">11</span>
<span style="color: rgba(0, 128, 128, 1)">12</span> <span style="color: rgba(0, 0, 0, 1)">.macro swap(%a,%b)
</span><span style="color: rgba(0, 128, 128, 1)">13</span> <span style="color: rgba(0, 0, 0, 1)">    move    $t0,%a
</span><span style="color: rgba(0, 128, 128, 1)">14</span> <span style="color: rgba(0, 0, 0, 1)">    move    %a,%b
</span><span style="color: rgba(0, 128, 128, 1)">15</span> <span style="color: rgba(0, 0, 0, 1)">    move    %b,$t0
</span><span style="color: rgba(0, 128, 128, 1)">16</span> <span style="color: rgba(0, 0, 0, 1)">.end_macro
</span><span style="color: rgba(0, 128, 128, 1)">17</span>
<span style="color: rgba(0, 128, 128, 1)">18</span> <span style="color: rgba(0, 0, 0, 1)">.macro load(%a)
</span><span style="color: rgba(0, 128, 128, 1)">19</span>   addi    $sp,$sp,<span style="color: rgba(128, 0, 128, 1)">4</span>
<span style="color: rgba(0, 128, 128, 1)">20</span> <span style="color: rgba(0, 0, 0, 1)">    lw    %a,($sp)
</span><span style="color: rgba(0, 128, 128, 1)">21</span> <span style="color: rgba(0, 0, 0, 1)">.end_macro
</span><span style="color: rgba(0, 128, 128, 1)">22</span>
<span style="color: rgba(0, 128, 128, 1)">23</span> <span style="color: rgba(0, 0, 0, 1)">.text
</span><span style="color: rgba(0, 128, 128, 1)">24</span>   li    $v0,<span style="color: rgba(128, 0, 128, 1)">5</span>
<span style="color: rgba(0, 128, 128, 1)">25</span>   <span style="color: rgba(0, 0, 255, 1)">syscall</span>
<span style="color: rgba(0, 128, 128, 1)">26</span> <span style="color: rgba(0, 0, 0, 1)">    move    $s0,$v0      #s0是n
</span><span style="color: rgba(0, 128, 128, 1)">27</span> <span style="color: rgba(0, 0, 0, 1)">    move    $a0,$v0
</span><span style="color: rgba(0, 128, 128, 1)">28</span> <span style="color: rgba(0, 0, 0, 1)">    la    $a1,_a
</span><span style="color: rgba(0, 128, 128, 1)">29</span> <span style="color: rgba(0, 0, 0, 1)">    la    $a2,_b
</span><span style="color: rgba(0, 128, 128, 1)">30</span> <span style="color: rgba(0, 0, 0, 1)">    la    $a3,_c      #配置四个参数:盘子数,from,tmp,to
</span><span style="color: rgba(0, 128, 128, 1)">31</span> <span style="color: rgba(0, 0, 0, 1)">    jal   dfs
</span><span style="color: rgba(0, 128, 128, 1)">32</span>   
<span style="color: rgba(0, 128, 128, 1)">33</span>   li    $v0,<span style="color: rgba(128, 0, 128, 1)">10</span>
<span style="color: rgba(0, 128, 128, 1)">34</span>   <span style="color: rgba(0, 0, 255, 1)">syscall</span>
<span style="color: rgba(0, 128, 128, 1)">35</span>
<span style="color: rgba(0, 128, 128, 1)">36</span> <span style="color: rgba(0, 128, 128, 1)">dfs:</span>
<span style="color: rgba(0, 128, 128, 1)">37</span>   bgt    $a0,<span style="color: rgba(128, 0, 128, 1)">1</span><span style="color: rgba(0, 0, 0, 1)">,dfs_work
</span><span style="color: rgba(0, 128, 128, 1)">38</span> <span style="color: rgba(0, 0, 0, 1)">    move    $a0,$a1
</span><span style="color: rgba(0, 128, 128, 1)">39</span>   li    $v0,<span style="color: rgba(128, 0, 128, 1)">4</span>
<span style="color: rgba(0, 128, 128, 1)">40</span>   <span style="color: rgba(0, 0, 255, 1)">syscall</span>
<span style="color: rgba(0, 128, 128, 1)">41</span> <span style="color: rgba(0, 0, 0, 1)">    la    $a0,connect
</span><span style="color: rgba(0, 128, 128, 1)">42</span>   li    $v0,<span style="color: rgba(128, 0, 128, 1)">4</span>
<span style="color: rgba(0, 128, 128, 1)">43</span>   <span style="color: rgba(0, 0, 255, 1)">syscall</span>
<span style="color: rgba(0, 128, 128, 1)">44</span> <span style="color: rgba(0, 0, 0, 1)">    move    $a0,$a3
</span><span style="color: rgba(0, 128, 128, 1)">45</span>   li    $v0,<span style="color: rgba(128, 0, 128, 1)">4</span>
<span style="color: rgba(0, 128, 128, 1)">46</span>   <span style="color: rgba(0, 0, 255, 1)">syscall</span>
<span style="color: rgba(0, 128, 128, 1)">47</span>   la    $a0,<span style="color: rgba(0, 0, 255, 1)">enter</span>
<span style="color: rgba(0, 128, 128, 1)">48</span>   li    $v0,<span style="color: rgba(128, 0, 128, 1)">4</span>
<span style="color: rgba(0, 128, 128, 1)">49</span>   <span style="color: rgba(0, 0, 255, 1)">syscall</span>
<span style="color: rgba(0, 128, 128, 1)">50</span>   jr    $<span style="color: rgba(128, 0, 128, 1)">31</span>
<span style="color: rgba(0, 128, 128, 1)">51</span>   
<span style="color: rgba(0, 128, 128, 1)">52</span> <span style="color: rgba(0, 128, 128, 1)">dfs_work:</span>
<span style="color: rgba(0, 128, 128, 1)">53</span>   save($<span style="color: rgba(128, 0, 128, 1)">31</span><span style="color: rgba(0, 0, 0, 1)">)
</span><span style="color: rgba(0, 128, 128, 1)">54</span> <span style="color: rgba(0, 0, 0, 1)">    save($a0)
</span><span style="color: rgba(0, 128, 128, 1)">55</span> <span style="color: rgba(0, 0, 0, 1)">    save($a1)
</span><span style="color: rgba(0, 128, 128, 1)">56</span> <span style="color: rgba(0, 0, 0, 1)">    save($a2)
</span><span style="color: rgba(0, 128, 128, 1)">57</span> <span style="color: rgba(0, 0, 0, 1)">    save($a3)
</span><span style="color: rgba(0, 128, 128, 1)">58</span>   addi    $a0,$a0,-<span style="color: rgba(128, 0, 128, 1)">1</span>
<span style="color: rgba(0, 128, 128, 1)">59</span> <span style="color: rgba(0, 0, 0, 1)">    swap($a2,$a3)
</span><span style="color: rgba(0, 128, 128, 1)">60</span> <span style="color: rgba(0, 0, 0, 1)">    jal    dfs
</span><span style="color: rgba(0, 128, 128, 1)">61</span> <span style="color: rgba(0, 0, 0, 1)">    load($a3)
</span><span style="color: rgba(0, 128, 128, 1)">62</span> <span style="color: rgba(0, 0, 0, 1)">    load($a2)
</span><span style="color: rgba(0, 128, 128, 1)">63</span> <span style="color: rgba(0, 0, 0, 1)">    load($a1)
</span><span style="color: rgba(0, 128, 128, 1)">64</span> <span style="color: rgba(0, 0, 0, 1)">    load($a0)
</span><span style="color: rgba(0, 128, 128, 1)">65</span>   load($<span style="color: rgba(128, 0, 128, 1)">31</span><span style="color: rgba(0, 0, 0, 1)">)
</span><span style="color: rgba(0, 128, 128, 1)">66</span>   
<span style="color: rgba(0, 128, 128, 1)">67</span>   save($<span style="color: rgba(128, 0, 128, 1)">31</span><span style="color: rgba(0, 0, 0, 1)">)
</span><span style="color: rgba(0, 128, 128, 1)">68</span> <span style="color: rgba(0, 0, 0, 1)">    save($a0)
</span><span style="color: rgba(0, 128, 128, 1)">69</span> <span style="color: rgba(0, 0, 0, 1)">    save($a1)
</span><span style="color: rgba(0, 128, 128, 1)">70</span> <span style="color: rgba(0, 0, 0, 1)">    save($a2)
</span><span style="color: rgba(0, 128, 128, 1)">71</span> <span style="color: rgba(0, 0, 0, 1)">    save($a3)
</span><span style="color: rgba(0, 128, 128, 1)">72</span>   li    $a0,<span style="color: rgba(128, 0, 128, 1)">1</span>
<span style="color: rgba(0, 128, 128, 1)">73</span> <span style="color: rgba(0, 0, 0, 1)">    jal    dfs
</span><span style="color: rgba(0, 128, 128, 1)">74</span> <span style="color: rgba(0, 0, 0, 1)">    load($a3)
</span><span style="color: rgba(0, 128, 128, 1)">75</span> <span style="color: rgba(0, 0, 0, 1)">    load($a2)
</span><span style="color: rgba(0, 128, 128, 1)">76</span> <span style="color: rgba(0, 0, 0, 1)">    load($a1)
</span><span style="color: rgba(0, 128, 128, 1)">77</span> <span style="color: rgba(0, 0, 0, 1)">    load($a0)
</span><span style="color: rgba(0, 128, 128, 1)">78</span>   load($<span style="color: rgba(128, 0, 128, 1)">31</span><span style="color: rgba(0, 0, 0, 1)">)
</span><span style="color: rgba(0, 128, 128, 1)">79</span>   
<span style="color: rgba(0, 128, 128, 1)">80</span>   save($<span style="color: rgba(128, 0, 128, 1)">31</span><span style="color: rgba(0, 0, 0, 1)">)
</span><span style="color: rgba(0, 128, 128, 1)">81</span> <span style="color: rgba(0, 0, 0, 1)">    save($a0)
</span><span style="color: rgba(0, 128, 128, 1)">82</span> <span style="color: rgba(0, 0, 0, 1)">    save($a1)
</span><span style="color: rgba(0, 128, 128, 1)">83</span> <span style="color: rgba(0, 0, 0, 1)">    save($a2)
</span><span style="color: rgba(0, 128, 128, 1)">84</span> <span style="color: rgba(0, 0, 0, 1)">    save($a3)
</span><span style="color: rgba(0, 128, 128, 1)">85</span>   addi    $a0,$a0,-<span style="color: rgba(128, 0, 128, 1)">1</span>
<span style="color: rgba(0, 128, 128, 1)">86</span> <span style="color: rgba(0, 0, 0, 1)">    swap($a1,$a2)
</span><span style="color: rgba(0, 128, 128, 1)">87</span> <span style="color: rgba(0, 0, 0, 1)">    jal    dfs
</span><span style="color: rgba(0, 128, 128, 1)">88</span> <span style="color: rgba(0, 0, 0, 1)">    load($a3)
</span><span style="color: rgba(0, 128, 128, 1)">89</span> <span style="color: rgba(0, 0, 0, 1)">    load($a2)
</span><span style="color: rgba(0, 128, 128, 1)">90</span> <span style="color: rgba(0, 0, 0, 1)">    load($a1)
</span><span style="color: rgba(0, 128, 128, 1)">91</span> <span style="color: rgba(0, 0, 0, 1)">    load($a0)
</span><span style="color: rgba(0, 128, 128, 1)">92</span>   load($<span style="color: rgba(128, 0, 128, 1)">31</span><span style="color: rgba(0, 0, 0, 1)">)
</span><span style="color: rgba(0, 128, 128, 1)">93</span>   
<span style="color: rgba(0, 128, 128, 1)">94</span>   jr    $<span style="color: rgba(128, 0, 128, 1)">31</span>
<span style="color: rgba(0, 128, 128, 1)">95</span>   </pre>
</div>
<p><strong><span style="font-size: 18px">&nbsp;课上测试部分:</span></strong></p>
<p><span style="font-size: 15px">第一题:阶乘求和,给定数n,求1!+2!+…………+n!&nbsp;这个实现起来还是挺简单的,毕竟二维数组和递归都能熟练操作了,二重循环不算啥了。</span></p>
<p><span style="font-size: 15px">第二题:单步汉诺塔,几乎压中。写过普通汉诺塔的那个题的汇编程序的话,这个题也就是十分钟吧。题目做出的改动是:只能相邻柱子之间移动。还好给了C代码,翻译起来和普通汉诺塔如出一辙。追根溯源可知,该题对应这里:https://accoding.cn/problem/1073/index&nbsp;是17级的一道程设题,上个星期还和室友讨论过……考场遇到研究过的问题是真的爽。</span></p>
<p><span style="font-size: 15px">第三题:高精度乘法,碰巧我也准备了C的代码,所以也不会费太多的事。这个题可能卡人的地方可能有同学不会写高精度乘法。不巧我之前的一篇博客介绍过……大家可以移步那里。</span></p><br><br>
来源:https://www.cnblogs.com/BUAA-Wander/p/11746238.html
頁: [1]
查看完整版本: P2-汇编语言