【算法】【算法杂谈】折纸问题(完全二叉树解法)

这篇具有很好参考价值的文章主要介绍了【算法】【算法杂谈】折纸问题(完全二叉树解法)。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

前言

当前所有算法都使用测试用例运行过,但是不保证100%的测试用例,如果存在问题务必联系批评指正~

在此感谢左大神让我对算法有了新的感悟认识!

问题介绍

原问题
一张纸从下往上对折之后,出现一条折痕,该折痕凸起向下,所以叫“下折痕”,反之如果摊开之后,凸起向上,则叫上折痕。
如果一张纸从下往上对折两次,则折痕为 [下,下,上]如下图所示
【算法】【算法杂谈】折纸问题(完全二叉树解法)
问:
给定整数num,表示这张纸按照从下往上折叠的方式折叠num次,摊开之后,从上往下的折痕方向顺序是什么?
如:
num = 2
结果为:下下上

解决方案

原问题
1、首先想一个问题,如果当前纸有一个向下的折痕,那么对于向下的折痕,我们再次对折时,在下面的纸张摊开后会形成向下的折痕,在上面的纸张会形成向上的折痕,因此我们能够确定,对于每一个向下的折痕都有这个规律
2、同理我们也可以发现,对于折叠好的向上的折痕,如果我们再次折叠会出现 下上上
3、综合上面,还有一个规律就是每一次的折叠都是对当前折痕中的上上下下再次进行折叠,所以通过当前折痕是上和下即可判断出折好之后的三元组是什么,如当前折痕是下,那么折叠好摊开一定是 下下上三元组,如果是上,那么一定是下上上三元组。
4、理解了上面三条我们就很容易的可以使用完全二叉树来进行折纸问题的计算,下图是折叠三次的示例
【算法】【算法杂谈】折纸问题(完全二叉树解法)

自己可以拿一张纸来折叠一下看看是不是这个规律,整体的就是这个完全二叉树的中序遍历!

代码编写

java语言版本

原问题:
方法一:

     /**
     * 二轮测试:纸张折叠num次之后,打印折痕
     * @param num
     */
    private static void printAllFoldersCp1(int num) {
        if (num <= 0) {
            return;
        }
        processCp1(num, null, null);
    }

    /**
     * 中序遍历,递归打印折痕
     * @param num
     * @param parent 父节点是上还是下
     * @param isLeft 是否左子节点
     */
    private static void processCp1(int num, Boolean parent, Boolean isLeft) {
        if (num == 0) {
            // 已经减到0了直接返回
            return;
        }
        Boolean cur = false;
        // 先判断自己的是上还是下
        if (parent == null || isLeft == null) {
            // 根节点直接下
            cur = false;
        }else if (!parent && isLeft) {
            // 根节点是下并且自己是左子树
            cur = false;
        }else if (!parent && !isLeft) {
            // 根节点是下,并且自己是右子树
            cur = true;
        }else if (parent && isLeft) {
            // 上左子树
            cur = false;
        }else if (parent && !isLeft) {
            cur = true;
        }
        // 判断完成后开始下一轮
        processCp1(num - 1, cur, true);
        // 输出自己
        System.out.println(cur ? "上" : "下");
        // 输出右边
        processCp1(num - 1, cur, false);
    }


    public static void main(String[] args) {
        printAllFolders(4);
    }

c语言版本

正在学习中

c++语言版本

正在学习中

思考感悟

发现规律是一个难点:这个规律文字其实解释起来很麻烦,但是如果自己找一张纸折叠一下就会发现其实过程就是一个递归的过程,
对折这个动作就非常的“递归”,当对折的时候折痕两边的纸片都会被折叠,同样是折叠,只是下面的纸片向上折叠,而上面的纸片其实是一个向下折叠的过程,因为摊开的过程是一个翻转的过程,这个需要自己去慢慢体会一下
构造遍历方式也是一个难点:第一想法是先构造一个完全二叉树再遍历,如此一来,感觉有点憨憨
那么接下来如何能够节省空间的中序遍历呢?
首先num = 3, 我们认为root节点高度为3,那么整体的顺序为 左子树 -> root -> 右子树
其次,构造递归函数的入参,第一个入参:num不解释,第二个入参,parent,第三个入参当前是左子节点还是右子节点
因为只有知道自己的父节点和自己的位置是左边还是右边才能计算出来自己当前应该是上还是下。

写在最后

方案和代码仅提供学习和思考使用,切勿随意滥用!如有错误和不合理的地方,务必批评指正~
如果需要git源码可邮件给2260755767@qq.com
再次感谢左大神对我算法的指点迷津!文章来源地址https://www.toymoban.com/news/detail-430149.html

到了这里,关于【算法】【算法杂谈】折纸问题(完全二叉树解法)的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 算法刷题Day 16 二叉树的最大深度+N叉树的最大深度+二叉树的最小深度+完全二叉树的节点个数

    递归法 迭代法 使用层序的方法,相对比较好理解 递归法 迭代法 跟二叉树的迭代差不多意思。 要想到是后序遍历 递归法 先计算左右两棵子树的节点数,再加和,用后序遍历的方法 迭代法 迭代法用层序遍历来处理 适用于完全二叉树的优化 完全二叉树优化方法没自己想出来

    2024年02月17日
    浏览(32)
  • 【算法与数据结构】222、LeetCode完全二叉树的节点个数

    所有的LeetCode题解索引,可以看这篇文章——【算法和数据结构】LeetCode题解。    思路分析 :利用层序遍历,然后用num++记录节点数量。其他的例如递归法和迭代法也是如此。    层序遍历程序如下 : 复杂度分析: 时间复杂度: O ( n ) O(n) O ( n ) 。 空间复杂度: O ( n )

    2024年02月15日
    浏览(35)
  • 完全二叉树、完美二叉树、完满二叉树、计算完全二叉树的结点

    对于完美二叉树,我们常用的是另一个名称:满二叉树 完美二叉树的定义: 完美二叉树是一种特殊的完全二叉树,每层都是满的,像一个稳定的三角形 完全二叉树的定义: 全二叉树从根结点到倒数第二层满足完美二叉树,最后一层可以不完全填充,其叶子结点都靠左对齐。

    2023年04月08日
    浏览(68)
  • Java LeetCode篇-深入了解二叉树的经典解法(多种方式实现:构造二叉树)

    🔥博客主页: 【 小扳_-CSDN博客】 ❤感谢大家点赞👍收藏⭐评论✍     文章目录         1.0 从前序与中序遍历序列来构造二叉树         1.1 实现从前序与中序遍历序列来构造二叉树思路            1.2 代码实现从前序与中序遍历序列来构造二叉树         2.0 从中序

    2024年02月05日
    浏览(33)
  • ​LeetCode解法汇总823. 带因子的二叉树

    https://github.com/September26/java-algorithms 给出一个含有不重复整数元素的数组  arr  ,每个整数  arr[i]  均大于 1。 用这些整数来构建二叉树,每个整数可以使用任意次数。其中:每个非叶结点的值应等于它的两个子结点的值的乘积。 满足条件的二叉树一共有多少个?答案可能很

    2024年02月10日
    浏览(25)
  • Java LeetCode篇-二叉树经典解法(实现:判断平衡二叉树、找两个节点最近的祖先等)

    🔥博客主页: 【 小扳_-CSDN博客】 ❤感谢大家点赞👍收藏⭐评论✍     文章目录         1.0 平衡二叉树         1.1 实现判断平衡二叉树的思路         1.2 代码实现判断平衡二叉树         2.0 二叉树的层序遍历         2.1 实现二叉树层序遍历的思路          2.2

    2024年02月05日
    浏览(35)
  • Java LeetCode篇-深入了解二叉树经典解法(三种方式实现:获取二叉树的最大深度)

    🔥博客主页: 【 小扳_-CSDN博客】 ❤感谢大家点赞👍收藏⭐评论✍    文章目录         1.0 对称二叉树         1.1 判断对称二叉树实现思路         1.2 代码实现:判断对称二叉树         2.0 二叉树的最大深度         2.1 使用递归实现获取二叉树的最大深度思

    2024年02月05日
    浏览(32)
  • 二叉树的概念|满二叉树与完全二叉树|二叉树的性质|二叉树的存储结构

    在数据结构中树的用途其实并不大,用得更多的其实是二叉树。所以在本章我们将详细讲解二叉树。 一颗二叉树是结点的一个 有限集合 ,该集合: 或者为空 或者由一个根节点加上两颗(互不相交)别称为左子树和右子树的二叉树组成 如图我们可知, 二叉树的特点: 二叉

    2024年01月21日
    浏览(33)
  • 【完全二叉树节点数!】【深度优先】【广度优先】Leetcode 222 完全二叉树的节点个数

    ---------------🎈🎈题目链接🎈🎈------------------- 完全二叉树只有两种情况: 情况一:就是满二叉树, 情况二:最后一层叶子节点没有满。 对于情况一,可以直接用 2 ^ 树深度 - 1 来计算,注意这里根节点深度为1。 对于情况二,分别递归左孩子,和右孩子,递归到某一深度一

    2024年02月19日
    浏览(25)
  • ​LeetCode解法汇总2385. 感染二叉树需要的总时间

    https://github.com/September26/java-algorithms 给你一棵二叉树的根节点  root  ,二叉树中节点的值  互不相同  。另给你一个整数  start  。在第  0  分钟, 感染  将会从值为  start  的节点开始爆发。 每分钟,如果节点满足以下全部条件,就会被感染: 节点此前还没有感染。 节点

    2024年04月24日
    浏览(24)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包