美文网首页
数据结构结课作业日记

数据结构结课作业日记

作者: 讲故事的万物 | 来源:发表于2020-06-03 18:11 被阅读0次

直到昨天中午,我还在因为读错题而疯狂学习新知识。

把整个任务脑补成了一个巨大的任务的错误太可怕了,以后要记住这次的教训,简直是白费了一天多的功夫。

不过这两天也不仅仅做这个任务,还复习了计算机网络,但是考试居然不是今天,是下周的今天。

这种事情怎么老是搞错呢。。。

算了都是好事不在意它。

结课作业中的问题

长久不用C语言,导致语言基础爆炸,很多东西忘记怎么使用,频频报错。

写两篇日志,分别是C语言的语法方面的问题和C语言算法的问题,本篇是语法问题。

指针和数组

这个问题一直是问题,在学C语言的时候草草就过去了,没有细致探讨,这里进行一定的实用性探讨。

  1. 数组名是数组首元素地址
    数组名和指针一样,存储的是地址,特殊在数组名内存储的是数组本身首元素的地址。
    一个词叫做解引用,把一个地址对应的数据取出就是解引用。
    对于一个数组a[N],我们进行了三步:第一步,取出数组元素首地址;第二步,目标地址=首地址+sizeof(type)*N,得到目标a[N]的地址;第三步,对地址解引用。
    对于一个指针p,只有两步,对p的地址解引用,获取到p的值,也就是p指向目标的地址;再对这个目标地址再次解引用,获得目标元素。

数组名!=数组指针,而是等于数组首元素指针。

  1. 一维数组可以和一维指针混用,二维数组可以喝二维指针混用吗?不可!

首先我们强调,把多维数组当做一维数组看待。
比如char arr[3][3],我们就要把它当做一维数组,内里元素分别为arr[0]arr[1]arr[2],这三个char [3]型的数组。

为什么?
我们先来看二维数组名代表了什么在代码中:

代码1:
char buf[2][2]={{1,2},{3,4}};
char *p = buf;
编译结果:

warning: initialization from incompatible pointer type [-Wincompatible-pointer-types]

代码2:
char buf[2][2]={{1,2},{3,4}};
char (*p)[2] = buf;
编译结果:
无警告信息

显然,二位数组的数组名指针类型是char*[2]型,我们应当把二维乃至多维数组看成嵌套型的一维数组,也就是俄罗斯套娃数组,我们可以看到,数组名指针指向的首元素指针既可以是普通变量,也可以是一维或多维数组。

  1. 那么如何用指针来指向数组呢?
    数组中的元素排列是顺序排列的,也就是一横排一横排连续,所以有以下代码可以用指针指向数组并且调用。
#include<stdio.h>
#include<stdlib.h>

#define ROW 2
#define COLUMN 2
int main(void)
{
    char buf[ROW][COLUMN]={{1,2},{3,4}};
char *p = (char*)buf;
//访问buf[x][y],即访问p[x*COLUMN+y]
printf("buf = %d,%d,%d,%d\r\n",p[COLUMN*0+0],p[COLUMN*0+1],p[COLUMN*1+0],p[COLUMN*1+1]);
system("pause");
return 0;
}

结果是这样



通过这个试验,我们可以了解到如何用指针来管理数组了。

指针传递、引用传递

函数中有各种参数,普通的直接调用没有什么可说的,仅仅是新建一个值,只存活在函数调用期间,而函数麻烦而又有用的地方就在这指针传递和引用传递。

  1. 二者有什么共同点?
    都是在函数中操作实参地址的,而值传递操作的不是实参地址。

  2. 有什么不同点?
    引用的规则是被引用的同时必须被初始化,同时不能有NULL引用,引用必须与合法的存储单元关联。
    一旦引用倍初始化,就不能改变引用的关系。
    而指针可以任何时候被初始化,可以是NULL,可以随时改变所指的对象。

  3. 二者不同的根本原因。
    从概念上讲。指针从本质上讲就是存放变量地址的一个变量,在逻辑上是独立的,它可以被改变,包括其所指向的地址的改变和其指向的地址中所存放的数据的改变。

    而引用是一个别名,它在逻辑上不是独立的,它的存在具有依附性,所以引用必须在一开始就被初始化,而且其引用的对象在其整个生命周期中是不能被改变的(自始至终只能依附于同一个变量)。

用一段这个函数,展示下使用流程。

#include<stdio.h>
#include<stdlib.h>

#define ROW 2
#define COLUMN 2

typedef struct TEST
{
    int a;
    int b[5];
    int *c;
}testOf;

void tt(testOf *t);
void ttt(testOf &t);
int main(void)
{
    testOf testa,testb;
    testOf *te;
    testOf *teb=&testb;
    te=&testa;
    testa.a=8;
    for(int i=0;i<5;i++){
    tt(te);
    ttt(testa);
    ttt(testb);
    tt(teb);
    }
    teb=te;
    
    printf("%d%d\n",testa.a,testa.c);
    system("pause");

    return 0;
}
void tt(testOf *t)
{
    
    t->a++;
    printf("%d\n",t->a);

    t->c=&t->a;
}
void ttt(testOf &t)
{
    t.a=100;
    printf("%d\n",t.a);

}

函数多返回值

很多时候,我们都会碰到一个函数需要多个返回值,但是一个函数的返回值只有一个,如何用一个函数返回多个值呢?

想到指针就对了,我们可以在参数中使用指针参数,传递我们主函数中的参数,通过这个函数来影响实参。

我很喜欢一句话就是“编程的本质不就是改变量吗?”先有量的输入,然后改变成很多量,变型、变数、计算都是改变量。

输入流

输出的方法千篇一律,大多时候就是好看点和不好看的区别。

每次写c的时候,做题没感觉,但是只要是写整个程序就会出现各种难受的问题,最大的问题就是输入的问题。

如何能够方便输入、快速输入经常会成为一个大问题。

如何能够快速输入呢?
我们就想到一个方法,用空格隔开数组中的每一个数,用回车来确定。
这样不仅能清晰看到我们的输入,也比一直敲数字敲回车优雅。

粗略代码如下

#include <stdio.h>
int main(){
    int num;
    int i=0;
    int arr[10];
   while(1){
        scanf("%d",&num);
        char c=getchar();
        arr[i++]=num;
        if(c=='\n'){
            break;
        }
   }
  return 0;
}

getchar();读走了空格和回车并且在下面判定,空格再次循环,回车退出。

因为这次是为了给结课作业中的二维数组邻接表做输入,我就简单再写一个给二维数组邻接表赋值的详细代码。

#include<stdio.h>
#include<stdlib.h>

#define MAX_V_NUM 10
#define MAX_INT 999 //不可能数
//#define MAX_CITY_NUM 10

typedef struct TEST
{
    char chengshi[20] ;
    int arcsM[MAX_V_NUM][MAX_V_NUM];
    int Vnum,Lnum;
    int *c;
}testOf;

/*
typedef struct CITY
{
    testOf city[MAX_CITY_NUM];
}TheWord
*/

void init(testOf *map);//初始化邻接表,每个点到其他店为不可能值,到自己为0;
void mapIn(testOf &map);//手动输入邻接表,按行输入,空格分开数,回车分开行。
void mapShow(testOf *map);//展示邻接表



int main(void)
{
    testOf map,arcs;
    testOf *pmap;
    testOf *parcs;
    pmap=&map;
    parcs=&arcs;

    init(pmap);
    mapShow(pmap);
    mapIn(map);
    mapShow(pmap);

    system("pause");
    return 0;
}

/*初始化邻接表,*/
void init(testOf *map)
{
    int i,j;
    map->Vnum=MAX_V_NUM;
    for(i=0;i<MAX_V_NUM;i++)    //邻接矩阵的初始化
    {
        for(j=0;j<MAX_V_NUM;j++)
        {
            if(i==j)
            {
                map->arcsM[i][j]=0;
            }
            else
            {
                map->arcsM[i][j]=MAX_INT;
            }
        }
    }
}

/*手动输入邻接表*/
void mapIn(testOf &map)
{
    int num;
    int i=0;
    int j=0;
    int Vtime;
    printf("请输入城市中重要站点的数目\n");
    scanf("%d",&map.Vnum);
    Vtime=map.Vnum;
    getchar();

    printf("请输入邻接表值,格式为1 2 3 4,将这4个数赋值给邻接矩阵第一排\n");

/*为邻接表手动赋值,0代表不改变*/
    for(i=0;i<map.Vnum;i++) 
    {   
        printf("现在是第%d行,共有%d行\n",i+1,map.Vnum);
        for(j=0;j<map.Vnum;j++)
        {
            scanf("%d",&num);
            char c=getchar();

            if(num!=0 && map.arcsM[i][j]!=0)
            {
                map.arcsM[i][j]=num;
            }
            /*
            if(c==' '){
                Vtime--;
                if(Vtime==1){
                    break;
                }
            }
            */
            if(c=='\n'){
                break;
            }
        }
    }
}

/*展示邻接表*/
void mapShow(testOf *map)
{
    printf("--------此表如下----------\n");
    int i,j;
        for(i=0;i<map->Vnum;i++)    
    {   

        for(j=0;j<map->Vnum;j++)
        {
            printf("%d ",map->arcsM[i][j]);
        }
        printf("\n");
    }
}
这段代码实现了通过空格隔开数据,分行输入数据到数组中,效果如下

虽然没有鲁棒性,没有错误显示,不过有了一个大的架子,试验中使用还是足够的。

本次实验期间任务繁多,如果在最后较为空闲,会补出等同这段代码,会更加美观更加健壮。


以下是我遇到问题后,上网查资料帮助到我的文章。

————————————————
版权声明:本文为CSDN博主「千淘万漉」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/matrix_google/article/details/76595439
————————————————
版权声明:本文为CSDN博主「魏波-」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/weibo1230123/article/details/75541862

相关文章

  • 数据结构结课作业日记

    直到昨天中午,我还在因为读错题而疯狂学习新知识。 把整个任务脑补成了一个巨大的任务的错误太可怕了,以后要记住这次的...

  • 结课作业

    很多时候也并不觉得自己拖拉,但做起事来一旦停下就会和完成的那一天相隔遥遥。我可以一直坐着耐心认真完成,可一旦打断,...

  • 结课作业

    35岁开始学游泳,第一次换了泳衣站在泳池边战战兢兢,跟着教练比划手和脚的动作,像小学生一样一板一眼认认真真,然后背...

  • 结课作业

    结课作业发下来,总体评语不错,但没有加精成优秀,估计这种小切囗文章不是老师提倡的那类大散文。但我很高兴,因为文末一...

  • 速写

    公选课结课作业

  • 我想逃离冬天

    2018.12.27 星期四 南京 阴 今天来写一则日记。 年底结课、考试、交作业真的太忙了,刚才考完二外回到宿舍...

  • 浙江大学-数据结构(基础)-笔记:连载中...

    第一堂课:数据结构定义 1.1 什么是数据结构关于数据结构的定义很多,至今都没有统一的定义 [Sahni-《数据结...

  • 人物班结课作业,被老师pass掉的作品

    这幅作品,是我人物班的结课作业,刚起完型,就被老师pass掉了。 这次结课作业,我满怀信心地挑了这幅素材。线稿画好...

  • 拖延症

    上上个周四就结课了,老师布置完结课作业,我就决定这次一定要早早地把作业搞完,早弄完早安心。结果是,直到现在,结课作...

  • 彩铅风景班复盘⑦:第六幅习作(街景)

    这是彩铅风景班复盘的第六幅习作(街景),也是这期风景班的结课作业,时间过得真快,不知不觉又到画结课作业的最后关头,...

网友评论

      本文标题:数据结构结课作业日记

      本文链接:https://www.haomeiwen.com/subject/pdfvzhtx.html