Homework_02

 

先谈谈感想

  这次作业是第一次作业的一个拓展,本以为至少会思路比较清晰,可谁想到,清晰的只是第二问,问题到了第三问(即关于“/a”),貌似就突然由量变到了质变,该算法貌似到了一个我难以企及的高度。笔者思索了近一个星期,零零碎碎的时间加起来估摸着得有6-7个小时,去思考关于第三问的算法。可结果,算法复杂度依旧是那么的不喜人。没办法,只好去询问一些知名的大神,特此,才勉强得出一个看得过去的算法。但是暂时依旧没能算法实现,在此只提下算法的思想,具体的代码实现由后续的版本持续更新。


第三问算法思想

 

  第三问的思想,我问了很多大神,有些人告诉我用连通性状态压缩,有些人告诉我直接暴力搜索。经过众多大神的指导与启发,我知道了一种用贪心加暴搜的方法,可以在原有的暴搜基础上,通过贪心优化,再此特别感谢梁杰大神。

  算法核心思想如下:

    1. 定义基点的概念。每一个连通图,对应的由一个起始点发展起来,这个起始点就叫做基点。定义新的数据结构dot,为二维数组中纵坐标,横坐标,以及在数组中的值。

    2. 第一次筛选,易知每个基点必须要是正数,否则,我可以弱全都是负数的话,我可以去最大的负数,即为所要的解。将这些书以队列的形式存在positiveNum[](数据类型为dot)里,。

    3.定义一个数组getableNum[],数据类型为dot,该数组用于存储可以延拓的点,但值一定是正数。

    4.定义一个数组validNegativeDot[],数据类型为dot,该数组用于存储值为负数,但该店周围有比它该负数更大的正数。

    5.定义一个数组path[],数据类型为dot,该数组用于记录连通图的路径。

    6.算法,

        a.初始化,先从positiveNum[]中取出一个基点,添加入path[]。

        b.搜索该基点附近四个方位(上下左右)可以到达的点,其中值为正则存入getableNum[]里面,为负则存入validNegativeDot[]里面。

        c.判定validNegativeDot[]里面的负数点是否是有效的,若有效,则将该数组周围最小的整数点,存入getableNum[]里面,并且该负数点添加入path[],然后更新validNegativeDot[]数组。

        d.用广度优先搜索,将getableNum[]里面的点作为二次基点,重复a,b步骤。

        e.直到getableNum[]和validNegativeDot[]里面没有任何点。计算此时path[]里面所有值得加和与maxSum比较大小,更新maxSum。然后再取出positiveNum[]的一个点,重复上述步骤。

        f.直至positiveNum[]里面也没有值,算法宣布结束,此时的maxSum所要求的连通性最大子数组。

        


 

关于输入

  这次作业还有一个很蛋疼的地方就是他的输入,因为老师要求,如果输入文件的参数有错误, 这个程序应该能正常退出, 并显示相应的错误信息, 任何输入错误都不能导致你的程序崩溃。本身C语言读字符串就蛋疼,再加上该要求输入就变得异乎寻常的蛋疼。最终统计,输入大概写了一个多小时,约100行。

代码:

  1 for (i=1;i<argc-1;i++)
  2     {
  3         if (!strcmp(argv[i],"/v"))
  4             isV = 1;
  5         else if (!strcmp(argv[i],"/h"))
  6             isH = 1;
  7         else if (!strcmp(argv[i],"/a"))
  8             isA = 1;
  9         else{
 10             printf("command input error\n");
 11             return 0;
 12         }
 13     }
 14 
 15     //File input
 16     if((in = fopen(argv[argc-1], "r")) == NULL){
 17         printf("file open failed\n");
 18         return 0;
 19     }
 20     //row and line input
 21     if(fgets(read, 256, in) == NULL){
 22         printf("ERROR: file input error\n");
 23         return 0;
 24     }
 25     line = convertToNum(read);
 26     if(fgets(read, 256, in) == NULL){
 27         printf("ERROR: file input error\n");
 28         return 0;
 29     }
 30     row = convertToNum(read);
 31 
 32     //Main array input
 33     for (i=0;i<line;i++)
 34     {
 35         
 36         //getline
 37         if(fgets(read, 256, in) == NULL){
 38             printf("ERROR: file input error\n");
 39             return 0;
 40         }
 41         
 42         length = strlen(read);
 43         temp =0;
 44         flag=0;
 45         for(j=0;j<length;j++)
 46         {
 47             if(read[j]<='9'&&read[j]>='0'&& flag==0)
 48                 input[i][temp] = input[i][temp]*10+read[j]-'0';
 49 
 50             else if(read[j]<='9'&&read[j]>='0'&& flag==1)
 51             {
 52                 input[i][temp] = -input[i][temp];
 53                 input[i][temp] = -(input[i][temp]*10+read[j]-'0');
 54 
 55             }
 56             else if(read[j] == ','||read[j]=='')
 57             {
 58                 temp++;
 59                 flag=0;
 60             }
 61             else if(read[j]=='-')
 62                 flag=1;
 63         }
 64         if(temp<row-1)
 65         {
 66             printf("ERROR: file input error\n");
 67             return 0;
 68         }
 69     }
 70     //closefile
 71     fclose(in);
 72 
 73 
 74 
 75     for (i=0;i<line;i++)
 76     {
 77         for(j=0;j<row;j++)
 78             printf("%d ",input[i][j]);
 79         printf("\n");
 80     }
 81     
 82     switch (choose(isV,isH,isA))
 83     {
 84     case 1 :
 85         maxSum_1();return 1;
 86     case 2 :
 87         maxSum_2();return 1;
 88     case 3:
 89         maxSum_3();return 1;
 90     default:
 91         printf("ERROR:command input error");
 92         return 0;
 93     }
 94 
 95     
 96     //input 
 97      
 98 }
 99 int convertToNum(char charArr[])
100 {
101     int result=0;
102     int length,i;
103     length = strlen(charArr);
104     
105     for(i=0;i<length-1;i++)
106     {
107         if(charArr[i]<='9'&&charArr[i]>='0')
108             result = result*10+charArr[i]-'0';
109         else if(charArr[i] == ',')
110             return result;
111     }
112     return -1;
113 }

关于除第三次作业以外的作业

  这个简单写写,因为算法都基本一样。

  特别点的地方是,我才用了分模块的方式,因为根据我的考虑我有了/v和/h和不加有一点区别,所以我才用了3个函数

  其中,什么参数都不加的由maxSum_1函数完成,至少有/v和/h中一个但不含/a由maxSum_2函数完成,有/a由maxSum_3完成,但是maxSum_3现在还未实现。

maxSum_2具体代码如下:

 1 int max,maxend;
 2     int ult,super,tmpsum;
 3     int i,j,k,m;
 4     ult = input[0][0];
 5     for(i = 0; i < line; i++){
 6         for(j = i; j < (isV ? line+i : line); j++){
 7             super = input[0][0];
 8             for(m = 0; m < (isH ? row : 1); m++){
 9                 max = sum(line, row, i, j, m);
10                 maxend = max;
11                 for(k = m+1; k < (isH ? row+m : row); k++){
12                     tmpsum = sum(line, row, i, j, k);
13                     maxend = maxend+tmpsum > tmpsum ? maxend+tmpsum : tmpsum;
14                     max = max > maxend ? max : maxend;
15                 }
16                 super = max > super ? max : super;
17             }
18             ult = super > ult ? super : ult;
19         }
20     }
21     printf("%d\n", ult);

 

 测试结果

  测试用例:

  

  测试结果:

  


 

单元测试和代码覆盖率:

  这个还真不知道是个什么东西,希望老师或助教能够解释下。。。


 

项目时间

 

Personal Software Process Stages

时间百分比(%)

实际花费的时间 (分钟)

原来估计的时间 (分钟)

Planning

计划

 

 

 

Estimate

估计这个任务需要多少时间,把工作细化并大致排序

 2

 20 min

10 min

Development

开发

 

 

 

Analysis

  需求分析 (包括学习新技术)

 1

 10 min

20 min

Design Spec

生成设计文档

 0

 0 min

0 min

Design Review

 设计复审 (和同事审核设计文档)

 0

 0 min

0 min

Coding Standard

 代码规范 (制定合适的规范)

 3

 30 min

20 min

Design

 具体设计

 11

100 min

60 min

Coding

 具体编码

 32

 320 min

200 min

Code Review

代码复审

 22

 200 min

150 min

·         Test

测试(自我测试,修改代码,提交修改)

 

 150 min

120 min

Reporting

总结报告

 

 

 

·         Test Report

测试报告

 13

 120 min

100 min

·         Size Measurement

计算工作量

 1

 10 min

10 min

·         Postmortem & Improvement Plan

事后总结, 并提出改进

 1

 10 min

10 min

Total

总计

100%

1000min

700min

 

 

 

posted @ 2013-10-01 11:18  GrainLee  阅读(241)  评论(2编辑  收藏  举报