软构Lab1 实验报告


实验目标概述

本次实验通过求解三个问题,训练基本 Java 编程技能,能够利用 Java OO 开发基本的功能模块,能够阅读理解已有代码框架并根据功能需求补全代码,能够为所开发的代码编写基本的测试程序并完成测试,初步保证所开发代码的正确性。另一方面,利用 Git 作为代码配置管理的工具,学会 Git 的基本使用方法。

 

实验环境配置

在官网上下载IDEA、JDK和Git并安装,IDEA内自有JUnit,直接下载即可。在为JDK配置环境变量的时候,在系统环境变量中新建一个“JAVA_HOME”环境变量,变量值为JDK的安装路径。然后在Path的环境变量中添加一个“%JAVA_HOME%bin”的变量值。

 

在这里给出你的GitHub Lab1仓库的URL地址:

实验过程

请仔细对照实验手册,针对四个问题中的每一项任务,在下面各节中记录你的实验过程、阐述你的设计思路和问题求解思路,可辅之以示意图或关键源代码加以说明(但无需把你的源代码全部粘贴过来!)。

为了条理清晰,可根据需要在各节增加三级标题。

3.1 Magic Squares

幻方是一个n*n的方阵,每个元素都是正整数,且每行每列和两个对角线上的元素的和相等。该实验要求写出程序判断输入一个矩阵是否是幻方,并且写出构造奇数阶幻方的代码(该代码实现方法已经给出,只需理解实现方法并修改代码判断输入的值是否符合要求即可),并用所写的判断程序判断生成的是否是幻方。

 

3.1.1 isLegalMagicSquare()

第一步:先判断读取的是不是方阵。先读取文件,获取输入的“矩阵”的行数,实现方法是逐行读取,直至读空;接下来以行数为基准,再次读取文件,并以/t为分隔符,将各个元素分隔开,获得每行的列数,与之前所得的行数作比较。

第二步:判断各个元素值是否符合要求(正整数)。实现方法是利用正整数的正则表达式^[1-9][0-9]*与各个元素作比较,不符合要求则报错返回。

第三步:判断各行各列及对角元素的和是否相等。实现方法是先将各个元素转换成int型存储在n*n的二维数组中,再逐行逐列以及对角线元素求和并比较。实现代码见下,实现过程中通过以第一行元素和为基准与其余所求值1比较来判断:

 

for (int j = 0; j < n; j++)
    row_sum[0] += array[0][j];
int sum = row_sum[0];//以第一行的和为基准,与其余所求值比较判断

//计算每行的和
for (int i = 1; i < n; i++) {
    for (int j = 0; j < n; j++)
        row_sum[i] += array[i][j];
    if(row_sum[i] != sum) {
        System.out.println("error:sums of rows are not equal, " + fileName + " is not a magic square");
        return false;
    }
}

//计算每列的和
for (int j = 0; j < n; j++){
    for (int i = 0; i < n; i++)
        col_sum[j] += array[i][j];
    if(col_sum[j] != sum){
        System.out.println("error:sums of columns are not equal to the rows', " + fileName + " is not a magic square");
        return false;
    }
}

//主对角线和
for (int i = 0; i < n; i++)
    main_dia += array[i][i];
if(main_dia != sum){
    System.out.println("error:sum of main diagonal is not equal to the rows' and columns', " + fileName + " is not a magic square");
    return false;
}
//次对角线和
for (int i = 0; i < n; i++)
    minor_dia += array[n - 1 - i][i];
if(minor_dia != sum){
    System.out.println("error:sum of minor diagonal is not equal to the rows' and columns', " + fileName + " is not a magic square");
    return false;
}

 

3.1.2 generateMagicSquare()

该函数功能是生成一个奇数阶的幻方,具体实现方法已直接给出,实现方式可理解为从第一行中间位置开始,依次为矩阵右上方位置赋值,每次赋值加一。若当前为右边界,则赋值到左边界的相应行;若当前为上边界,则赋值到下边界的相应列;若对应右上元素已经被赋值(每n次赋值就会遇到一次),则赋值到当前元素的相对下一行,并据此继续依次按上述方法赋值,直至完成方阵的全部赋值。由于生成的是奇数阶方阵,需要对原代码稍加补充,判断调用者所给的参数是否为正奇数,补充代码见下:

 

if (n % 2 == 0 || n < 0) {
    System.out.println("The input of the n is illegal, please input a positive odd number.");
    return false;
}

 

测试生成就一个5阶方阵,结果见下:

 软构Lab1 实验报告

该函数的逻辑流程图:

 

软构Lab1 实验报告

 

 

 

3.2 Turtle Graphics

 

通过git将已经写好的代码clone下来,通过实现drawSquare函数、calculateRegularPolygonAngle函数、drawRegularPolygon函数、calculateBearingToPoint函数、calculateBearingsh函数、convexHull函数、drawPersonalArt函数来完成所有的问题,同时还要通过TurtleSoupTest.java中的测试用例。

 

3.2.1 Problem 1: Clone and import

 

用git clone和代码地址即可获取该任务的代码到本地、并用git代码在本地创建git仓库和使用git管理本地开发。

 

3.2.2 Problem 3: Turtle graphics and drawSquare

 

函数drawSquare的实现要求利用forward和turn方法完成一个正方形的绘制。forward方法能够让小海龟在画面上前进给定单位距离,turn方法能够让小海龟右转向90度。

 

由于每次绘图开始时海龟朝向Y轴正方向,因此只需让小海龟前进sideLength个单位,再右转90度,重复4次即可完成一个正方形的绘制。

 

实现代码见下:

 

 

 软构Lab1 实验报告

3.2.3 Problem 5: Drawing polygons

该问题要求根据给出的正多边形边数,计算正多边形的内角度。

正n边形内角和为(n-2)*180°,故所求内角为((n-2)*180°)/n=180°-360°/n。

3.2.4 Problem 6: Calculating Bearings

该问题要求给出正多边形角度,计算正多边形边数,仍利用上述公式,反推即可得出边数,但是由于角度以double型数据存储,得出的边数值非正整数,用Math.round四舍五入即可。

3.2.5 Problem 7: Convex Hulls

凸包问题,要求计算包住点集所有点的最小点集集合。实现过程中主要利用calculateBearingToPoint函数来计算两点之间的角度。从最右上角的点开始,易知该点一定在所求集合内,从该点开始每次遍历所有点,找到从该点到其余各点中转角最小的点,该点即目标点,将目标点加入集合,此后再以该目标点为基准,继续上述过程,直到再次返回到最开始的点。若在遍历时发现了多个相同最小偏转角度的点,则以距离最远的点作为目标点。主要部分的实现代码见下:

 

1.1.1 Problem 5: Drawing polygons

 

该问题要求根据给出的正多边形边数,计算正多边形的内角度。

 

正n边形内角和为(n-2)*180°,故所求内角为((n-2)*180°)/n=180°-360°/n。

 

1.1.2 Problem 6: Calculating Bearings

 

该问题要求给出正多边形角度,计算正多边形边数,仍利用上述公式,反推即可得出边数,但是由于角度以double型数据存储,得出的边数值非正整数,用Math.round四舍五入即可。

 

1.1.3 Problem 7: Convex Hulls

 

凸包问题,要求计算包住点集所有点的最小点集集合。实现过程中主要利用calculateBearingToPoint函数来计算两点之间的角度。从最右上角的点开始,易知该点一定在所求集合内,从该点开始每次遍历所有点,找到从该点到其余各点中转角最小的点,该点即目标点,将目标点加入集合,此后再以该目标点为基准,继续上述过程,直到再次返回到最开始的点。若在遍历时发现了多个相同最小偏转角度的点,则以距离最远的点作为目标点。主要部分的实现代码见下:

软构Lab1 实验报告

 

3.2.6 Problem 8: Personal art

利用turn、forward就可以实现一些简单图像的绘画。个人的绘画内容如下图:

 软构Lab1 实验报告

 

原创文章,作者:kirin,如若转载,请注明出处:https://blog.ytso.com/267706.html

(0)
上一篇 2022年6月18日
下一篇 2022年6月18日

相关推荐

发表回复

登录后才能评论