c语言第一个小游戏:贪吃蛇小游戏03

我们为贪吃蛇的节点设置为一个结构体,构成贪吃蛇的身子的话我们使用链表,链表的每一个节点是一个结构体

显示贪吃蛇身子的一个节点

我们这边node就表示一个蛇的身体  就是一小节

输出结果如下

显示贪吃蛇完整身子

效果如下

代码实现

        这个hasSnakeNode(hang,lie)这个函数就是来判断当前这个坐标是否为蛇的身子的坐标,坐标带进去,如果符合return 1;那么返回1 到地图这里   1  的话就是ture 使hasSnakeNode这个函数生效,然后打印[ ]蛇身。那么函数封装的好处就是在于我们可以进行多个节点的判断

        宏观的看,每个坐标都会进入到hasSnakeNode(hang,lie)进行判断,如果行列坐标等于蛇身子的行列坐标,那么就返回1        我们会去想p的下一项是哪里操作的 请看main函数node1.next=&next2,这个是关键,才能遍历链表,暂时是静态的写链表,下一次我们用动态添加的方法进行添加节点

代码

#include <curses.h>

struct snack{

        int hang;

        int lie;

        struct snack *next;

};

struct snack node1 = {2,2,NULL};

struct snack node2 = {2,3,NULL};

struct snack node3 = {2,4,NULL};

void initgame()

{

        initscr();

        keypad(stdscr,1);

}

int  hasSnackNode(int i,int j)

{

        struct snack *p;

        p = &node1;

        while(p != NULL){

                if(p->hang==i && p->lie==j){

                        return 1;

                }

                p=p->next;

        }

        return 0;

}

void gamepic()

{

        int hang;

        int lie;

        for(hang=0;hang<20;hang++){

                if(hang == 0){

                        for(lie=0;lie<20;lie++){

                                printw("--");

 }

                 printw("\n");

                }

                if(hang>=0 && hang<=19){

                        for(lie=0;lie<=20;lie++){

                                 if(lie==0||lie==20){

                                         printw("|");

                                 }else if(hasSnackNode(hang,lie)){

                                        printw("[]");

                                 }

                                 else{

                                         printw("  ");

                                 }

                        }

                        printw("\n");

                }

                if(hang == 19){

                        for(lie=0;lie<20;lie++){

                                 printw("--");

                        }

                        printw("\n");

                }

          }

          printw("by shijintao");

   }

int main()

{

initgame();

                node1.next = &node2;

                node2.next = &node3;

                gamepic();

                getch();

                endwin();

                return 0;

}

但是这个太土了我们要进行优化

我们用封装函数的方法

显示贪吃蛇完整身子

优化代码

#include <curses.h>

#include <stdlib.h>

struct snake{

        int hang;

        int lie;

        struct snake *next;

};

struct snake *head;//全局变量

struct snake *tail;//全局变量

void initgame()

{

        initscr();

        keypad(stdscr,1);

}

int  hasSnakeNode(int i,int j)

{

        struct snake *p;

        p = head; //现在头节点是head  不是node1了  而且这个head是通过initSnake影响的,因为head是全局变量,所以可以使用head

        while(p != NULL){

                if(p->hang==i && p->lie==j){

                        return 1;

                }

                p=p->next;

        }

        return 0;

}

void gamepic()

{

        int hang;

        int lie;

        for(hang=0;hang<20;hang++){

                if(hang == 0){

                        for(lie=0;lie<20;lie++){

                                printw("--");

                        }

printw("\n");

                }

                if(hang>=0 && hang<=19){

                        for(lie=0;lie<=20;lie++){

                                 if(lie==0||lie==20){

                                         printw("|");

                                 }else if(hasSnakeNode(hang,lie)){

                                        printw("[]");

                                 }

                                 else{

                                         printw("  ");

                                 }

                        }

                        printw("\n");

                }

                if(hang == 19){

                        for(lie=0;lie<20;lie++){

                                 printw("--");

                        }

                        printw("\n");

                }

          }

          printw("by shijintao");

   }

void addNode()

{

        struct snake *new;

        new =(struct snake *)malloc(sizeof(struct snake));

        new->hang=tail->hang; //最先开始tail的值等于head

        new->lie=tail->lie+1;

        tail->next = new;

        tail = new;//每次改变tail的值

        new->next = NULL;

}

void  initSnake()

{

        head = (struct snake *)malloc(sizeof(struct snake));

        head->hang=2;

        head->lie=2;

        head->next=NULL;

        tail = head;

        addNode();

}

int main()

{

                initgame();

                initSnake();

                gamepic();

                getch();

                endwin();

                return 0;

}

代码优化的点:

将原先死板添加的,变成动态的添加节点,并进行封装,减少代码冗余

void  initSnake()

{

        head = (struct snake *)malloc(sizeof(struct snake));    

        head->hang=2;//这些都是设置初始值

        head->lie=2;

        head->next=NULL;

        tail = head;//蛇的初始状态头节点也是尾节点

        addNode(); //如果你不加这个的话  蛇的身子就只有一个,我觉得加一个也就是比较好看

}

void addNode()

{

        struct snake *new;

        new =(struct snake *)malloc(sizeof(struct snake));

        new->hang=tail->hang; //这个只是单纯的向右边加入,不考虑方向,以后回头来看不要被误导

        new->lie=tail->lie+1;

        tail->next = new;

        tail = new;//可以这样想每次新节点插入后这个tail的值(行和列)都会回到最上方全局变量的地方然后,tail的值是不会被刷新的,是一直被影响的,被上一个节点影响,随后保存信息,因为他是全局变量

        new->next = NULL;

}

initSnake()这个函数直接就是把蛇的头节点,也就是蛇的初始位置,hang、lie 都默认的设置好,就像我们玩贪吃蛇初始有个蛇停在那边,这个函数就是这个作用。

这两个函数搭配使用组成了蛇的身子,我们都说用动态创建链表要用到指针,且链表都是有头节点和尾节点,为了不容易出现错误 我们将头指针和尾指针设置为全局变量。

头节点是指针,我们需要为指针赋予一个内存空间,因为后面我们需要在尾点后方插入新的节点,那么我们需要将新节点每次开辟一个空间。

最先开始尾节点就是头节点

addNode是添加新节点到尾节点后边

我们将添加新节点,还有初始化贪吃蛇的行列,封装成了函数,直接调用函数即可在尾部添加新节点

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/web/79604.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

架构思维:通用架构模式_系统监控的设计

文章目录 引言什么是监控三大常见监控类型1. 次数监控2. 性能监控3. 可用率监控 落地监控1. 服务入口2. 服务内部3. 服务依赖 监控时间间隔的取舍小结 引言 架构思维&#xff1a;通用架构模式_从设计到代码构建稳如磐石的系统 架构思维&#xff1a;通用架构模式_稳如老狗的SDK…

精益数据分析(46/126):深入剖析用户生成内容(UGC)商业模式

精益数据分析&#xff08;46/126&#xff09;&#xff1a;深入剖析用户生成内容&#xff08;UGC&#xff09;商业模式 在创业与数据分析的征程中&#xff0c;每一种商业模式都蕴含着独特的价值与挑战。今天&#xff0c;我们依旧怀揣着共同进步的信念&#xff0c;深入研读《精益…

QMK键盘固件中LED锁定指示灯的配置与使用详解(实操部分+拓展)

QMK键盘固件中LED锁定指示灯的配置与使用详解 大家好!今天就跟大家一起探索QMK固件中LED锁定指示灯的配置与使用。无论你是键盘DIY新手还是老司机,相信这篇教程都能帮你解锁新技能! 一、基础配置:定义LED引脚 在QMK固件中配置LED锁定指示灯非常简单,只需在config.h文件…

CVE体系若消亡将如何影响网络安全防御格局

CVE体系的核心价值与当前危机 由MITRE运营的通用漏洞披露&#xff08;CVE&#xff09;项目的重要性不容低估。25年来&#xff0c;它始终是网络安全专业人员理解和缓解安全漏洞的基准参照系。通过提供标准化的漏洞命名与分类方法&#xff0c;这套体系为防御者建立了理解、优先级…

一周学完计算机网络之三:1、数据链路层概述

简单的概述 数据链路层是计算机网络体系结构中的第二层&#xff0c;它在物理层提供的基本服务基础上&#xff0c;负责将数据从一个节点可靠地传输到相邻节点。可以将其想象成一个负责在两个相邻的网络设备之间进行数据 “搬运” 和 “整理” 的 “快递中转站”。 几个重要概念…

✨WordToCard使用分享✨

https://www.wordtocard.com 家人们&#xff0c;今天发现了一个超好用的工具——WordToCard&#xff01;&#x1f61c; 它可以把WordToCard文档转换成漂亮的知识卡片&#xff0c;学习笔记、知识整理和内容分享都变得超轻松&#xff5e;&#x1f917; 支持各种WordToCard语法…

扩展:React 项目执行 yarn eject 后的 package.json 变化详解及参数解析

扩展&#xff1a;React 项目执行 yarn eject 后的 package.json 变化详解及参数解析 什么是 yarn eject&#xff1f;React 项目执行 yarn eject 后的 package.json 变化详解1. 脚本部分 Scripts 被替换2. 新增构建依赖 dependencies&#xff08;部分&#xff09;3. 新增 Babel …

[Java实战]Spring Boot 整合 Redis(十八)

[Java实战]Spring Boot 整合 Redis&#xff08;十八&#xff09; 在现代的分布式应用开发中&#xff0c;Redis 作为一种高性能的键值存储数据库&#xff0c;被广泛用于缓存、消息队列、排行榜等多种场景。Spring Boot 提供了强大的支持&#xff0c;使得整合 Redis 变得非常简单…

【氮化镓】GaN在不同电子能量损失的SHI辐射下的损伤

该文的主要发现和结论如下: GaN的再结晶特性 :GaN在离子撞击区域具有较高的再结晶倾向,这导致其形成永久损伤的阈值较高。在所有研究的电子能量损失 regime 下,GaN都表现出这种倾向,但在电子能量损失增加时,其效率会降低,尤其是在材料发生解离并形成N₂气泡时。 能量损失…

R语言实战第5章(1)

第一部分&#xff1a;数学、统计和字符处理函数 数学和统计函数&#xff1a;R提供了丰富的数学和统计函数&#xff0c;用于执行各种计算和分析。这些函数可以帮助用户快速完成复杂的数学运算、统计分析等任务&#xff0c;例如计算均值、方差、相关系数、进行假设检验等。字符处…

k8s术语之Horizontal Pod Autoscaling

应用的资源使用率通常都有高峰和低谷的时候&#xff0c;如何削峰填谷&#xff0c;提高整体的整体资源利用率&#xff0c;让service中的Pod个数自动调整呢&#xff1f;Horizontal Pod Autoscaling:使pod水平自动缩放。这个Object也是最能体现kubernetes之于传统运维价值的地方&a…

Linux复习笔记(三) 网络服务配置(web)

遇到的问题&#xff0c;都有解决方案&#xff0c;希望我的博客能为你提供一点帮助。 二、网络服务配置 2.3 web服务配置 2.3.1通信基础&#xff1a;HTTP协议与C/S架构&#xff08;了解&#xff09; ​​HTTP协议的核心作用​​ Web服务基于HTTP/HTTPS协议实现客户端&#xff…

9.1.领域驱动设计

目录 一、领域驱动设计核心哲学 战略设计与战术设计的分野 • 战略设计&#xff1a;限界上下文&#xff08;Bounded Context&#xff09;与上下文映射&#xff08;Context Mapping&#xff09; • 战术设计&#xff1a;实体、值对象、聚合根、领域服务的构建原则 统一语言&am…

CSS Layer 详解

CSS Layer 详解 前言 最近在整理CSS知识体系时&#xff0c;发现Layer这个特性特别有意思。它就像是给样式规则提供了一个专属的「VIP通道」&#xff0c;让我们能更优雅地解决样式冲突问题。今天我就用最通俗的语言&#xff0c;带大家全面了解这个CSS新特性。 什么是CSS Laye…

【Dv3Admin】工具视图配置文件解析

在开发后台管理系统时,处理复杂的 CRUD 操作是常见的需求。Django Rest Framework(DRF)通过 ModelViewSet 提供了基础的增删改查功能,但在实际应用中,往往需要扩展更多的功能,如批量操作、权限控制、查询优化等。dvadmin/utils/viewset.py 模块通过继承并扩展 ModelViewS…

‌云原生CAE软件

‌云原生CAE软件‌是一种在设计和实现时就充分考虑了云环境特点的软件&#xff0c;能够充分利用云资源&#xff0c;实现高效、可扩展和灵活的仿真分析。 定义和特点 云原生CAE软件是一种在云端构建和运行的CAE&#xff08;Computer Aided Engineering&#xff0c;计算机辅助工…

若依定制pdf生成实战

一、介绍 使用 Java Apache POI 将文字渲染到 Word 模板是一种常见的文档自动化技术&#xff0c;广泛应用于批量生成或定制 Word 文档的场景。使用aspose可以将word转成pdf从而达到定制化pdf的目的。 参考文档&#xff1a;java实现Word转Pdf&#xff08;Windows、Linux通用&a…

Redis再次开源!reids8.0.0一键安装脚本分享

准备工作 1. 下载 Redis 8 安装包 # Redis 8.0.0 示例&#xff08;请替换为实际版本&#xff09; http://download.redis.io/releases/redis-8.0.0.tar.gz一、脚本内容&#xff1a; #!/usr/bin/python # -*- coding: UTF-8 -*-import os import time import shutil import s…

stm32之BKP备份寄存器和RTC时钟

目录 1.时间戳1.1 Unix时间戳1.2 UTC/GMT1.3 时间戳转换**1.** time_t time(time_t*)**2.** struct tm* gmtime(const time_t*)**3.** struct tm* localtime(const time_t*)**4.** time_t mktime(struct tm*)**5.** char* ctime(const time_t*)**6.** char* asctime(const stru…

Android学习总结之算法篇八(二叉树和数组)

路径总和 import java.util.ArrayList; import java.util.List;// 定义二叉树节点类 class TreeNode {int val;TreeNode left;TreeNode right;// 构造函数&#xff0c;用于初始化节点值TreeNode(int x) {val x;} }public class PathSumProblems {// 路径总和 I&#xff1a;判…