力扣46 全排列 引发对JAVA对象引用的思考

先简单说一下本题思路:
数据结构:栈
算法:递归

使用深度遍历,得到全排列。要使用一个标记数组来标记某个数在本次递归中是否被使用,然后在下次递归前要取消标记。

class Solution {private  int[] flag;private List<List<Integer>> v = new ArrayList<>();private List<Integer> vv = new ArrayList<>();public List<List<Integer>> permute(int[] nums) {flag = new int[nums.length];dfs(nums);return v;}private void dfs(int [] nums){if(vv.size() == nums.length){// v.add(vv);v.add(new ArrayList<>(vv));return;}for(int i = 0; i < nums.length; i++){if(flag[i] == 0){flag[i] = 1;vv.add(nums[i]);dfs(nums); vv.remove(vv.size()-1);flag[i] = 0;} }}
}

重点看我注解的这段代码,之前用c++写程序习惯了,但是换到JAVA导致结果一直是空。仔细思考和查了下资料:

通过执行 v.add(vv);,实际上添加的是对列表 vv 的引用,而不是当前内容的快照。因为在整个 DFS 过程中 vv 不断被修改,所以在 v 中的所有条目最终都会成为同一个列表的引用——而一旦递归完成,这个列表就会是空的。
改成v.add(new ArrayList<>(vv))确保了存储在 v 中的每个排列在被添加到列表时都准确反映了当时的实际状态,而不是最后都指向同一个(最终为空的)列表 vv。

在Java中,对象(包括那些实现了List接口的对象,如ArrayList)是通过引用来操作的。将vv添加到v中时,若是直接添加vv,实际上添加的是vv这个列表的引用,而不是它此刻的内容拷贝。这意味着,随后对vv的所有修改(添加元素、删除元素等操作),都会反映在v中所保存的这个引用所指向的同一个列表对象上。

再向下引申一点,在c++中为什么直接用v.push_bcak(vv)就可以呢?
这是因为C++在这种情境下执行的是对象的复制(copy),而不是引用(或指针)的复制。对于C++的std::vector(或大多数标准容器),push_back方法会创建一个参数的副本,并将这个副本存入容器中。因此,在C++中不需要显式地从vv创建一个新的std::vector对象就可以直接使用push_back(vv),因为push_back便已自动完成了这一复制工作。

这种差异归根结底是由于Java和C++对对象和容器的操作语义不同。Java中的对象赋值通常是引用赋值,而C++中的赋值(包括容器中元素的插入)则是创建对象副本的复制操作。这也反映了Java和C++在内存管理和对象模型方面的根本区别。

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

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

相关文章

【踏雪无痕的痕六】——数学中有意思的问题

一、背景介绍 提出一个问题往往比解决一个问题更有意义&#xff0c;因为提出一个问题相当于提出了一个思考问题的维度&#xff1b;而解决一个问题是沿着这个维度将已有的知识串起来的过程 三、过程 1.数人数你会吗&#xff1f; 小名再第10位&#xff0c;小李再第15位&#…

Linux下SpringBoot项目部署(centos系统)

一、首先找到自己的sql文件&#xff0c;没有就从数据库挪进来 二、在Maven下打包一下&#xff08;点击package&#xff09;&#xff0c;看到BUILD SUCCESS就是打包好了 三、将上面两个文件分别挪到 linux 中对应的文件&#xff0c;没有就创建一个&#xff08;我的是spring_blog…

【微机原理与汇编语言】并行接口8255实验

一、实验目的 掌握可编程并行接口芯片8255的工作原理及初始化方法掌握8255在实际应用中的硬件连接及编程应用 二、实验要求 根据实验室现有条件&#xff0c;针对实验任务&#xff0c;设计实验方案并进行实现。 三、实验内容 启动0#计数器&#xff0c;每计5个数&#xff08…

攻防世界—webbaby详解

1.ssrf注入漏洞 ssrf&#xff08;服务端请求伪造&#xff09;是一种安全漏洞&#xff0c;攻击者通过该漏洞向受害服务器发出伪造的请求&#xff0c;从而访问并获取服务器上的资源&#xff0c;常见的ssrf攻击场景包括访问内部网络的服务&#xff0c;执行本地文件系统命令&#…

Android基础-消息分发机制

Android中的消息分发机制是系统内部用于处理各种事件和消息传递的一套复杂而精巧的机制。它涉及到多个组件和层次&#xff0c;确保了Android系统的高效运行和响应性。下面将详细阐述Android中的消息分发机制&#xff0c;内容将涵盖其核心组件、工作原理、执行流程等方面。 核心…

Linux基础指令磁盘管理002

LVM&#xff08;Logical Volume Manager&#xff09;是Linux系统中一种灵活的磁盘管理和存储解决方案&#xff0c;它允许用户在物理卷&#xff08;Physical Volumes, PV&#xff09;上创建卷组&#xff08;Volume Groups, VG&#xff09;&#xff0c;然后在卷组上创建逻辑卷&am…

双指针: 盛水最多的容器

目录 描述 解法 盛水最多的容器_牛客题霸_牛客网 描述 给定一个数组height&#xff0c;长度为n&#xff0c;每个数代表坐标轴中的一个点的高度&#xff0c;height[i]是在第i点的高度&#xff0c;请问&#xff0c;从中选2个高度与x轴组成的容器最多能容纳多少水 1.你不…

【python】ModuleNotFoundError: No Module Named ‘openyxl’

成功解决“ModuleNotFoundError: No Module Named ‘openyxl’”错误的全面指南 在Python编程中&#xff0c;遇到ModuleNotFoundError: No Module Named openyxl这样的错误通常意味着Python解释器无法找到名为openyxl的模块。然而&#xff0c;这里存在一个常见的拼写错误&#…

从0到1学Binder-Binder驱动初始化

文章目录 1. binder_alloc_shrinker_init2. debugfs_create_dir/debugfs_create_file3. init_binder_device4. init_binderfs 我的微信公众号“ZZH的Android”&#xff0c;还有更多 Android 系统源码解析的干货文章等着你&#xff0c;欢迎关注加入交流群。 binder驱动启动入口如…

蓝桥杯物联网竞赛_STM32L071KBU6_第十五届蓝桥杯物联网竞赛国赛代码解析

目录 前言&#xff1a;1、配置及代码&#xff1a;(1) A板&#xff1a;[1] CUBMX配置&#xff1a;[2] keil5代码&#xff1a; (2) B板&#xff1a;[1] CUBMX配置&#xff1a;[2] keil5代码&#xff1a; 2、代码解析&#xff1a; 前言&#xff1a; 这届国赛是目前为止最难一届&am…

计算机发展史 | 从起源到现代技术的演进

computer | Evolution from origins to modern technology 今天没有参考资料哈哈 PPT&#xff1a;&#xff08;评论区&#xff1f;&#xff09; 早期计算工具 算盘 -算盘是一种手动操作的计算辅助工具&#xff0c;起源于中国&#xff0c;迄今已有2600多年的历史&#xff0c;是…

实验9 静态路由配置

实验9 静态路由配置 一、 原理描述二、 实验目的三、 实验内容四、 实验配置五、 实验步骤 一、 原理描述 网络中的每个路由器都会维护一张路由表或转发表。路由表的表项记录着目的网络信息以及下一跳I 地址。路由表可以手动配置&#xff0c;也可以通过路由算法动态生成。静态…

使用 MDC 实现日志链路跟踪,包教包会!

在微服务环境中&#xff0c;我们经常使用 Skywalking、Spring Cloud Sleut 等去实现整体请求链路的追踪&#xff0c;但是这个整体运维成本高&#xff0c;架构复杂&#xff0c;本次我们来使用 MDC 通过 Log 来实现一个轻量级的会话事务跟踪功能&#xff0c;需要的朋友可以参考一…

小世界网络生成及其分析

研究背景: 小世界网络是一种介于规则网络和随机网络之间的网络模型,具有短平均路径和高聚集性的特点。这种网络模型被广泛应用于社交网络、互联网、生物网络等领域的研究中。研究小世界网络的生成和分析可以帮助我们理解和揭示复杂网络的结构和特性,以及网络中信息传播、动力…

数据驱动的未来:数据融合与平台化应用的探索

随着大数据时代的到来&#xff0c;数据驱动的决策制定已成为企业与组织的核心。本文探讨了数据驱动的概念&#xff0c;数据融合的技术及其重要性&#xff0c;并分析了平台化应用如何促进数据的有效利用和价值创造。 数据驱动的决策制定 在信息化时代的浪潮中&#xff0c;数据已…

Flutter之旅:探索安卓与跨平台开发的无限可能

随着移动互联网的飞速发展,移动应用开发已成为企业竞争的重要战场。在众多开发框架中,Flutter凭借其高效的性能和出色的跨平台能力,正引领着一场安卓与跨平台开发的奇幻之旅。本文将从Flutter的起源、特点、优势以及未来展望等方面,深入探讨Flutter在移动应用开发领域的无限…

su和sudu、三剑客中的sed、awk命令

一、用户授权 如果普通用户需要执行特殊操作&#xff0c;有两种方法&#xff1a; su -root 切换到root账户进行特殊操作&#xff0c;然后再回到普通用户 sudo 命令 su命令&#xff1a; 优点&#xff1a;使用简单 缺点&#xff1a;root密码容易泄露 普通用户执行操作不可控 su…

官宣!2024 MongoDB Developer Day来了!北上深三场等你集结!

北上深开发者 专为你们打造的 MongoDB Developer Day 来了&#xff01; 动手实操工作坊➕模型设计优化专场 学习 NoSQL 数据建模的最佳实践 深入探索 MongoDB 的各种可能性 和开发者同行和 MongoDB 技术专家 一起度过充实的一天&#xff01; 北京&#xff08;6/22&…

HBuilderx uniapp启动微信小程序报错[error] Error: Fail to open IDE

1、打开微信呢开发者工具&#xff0c;添加项目 创建小程序--目录&#xff08;目录选择自己小程序项目下的dist/dev/mp-weixin&#xff09;点击确定之后微信开发者工具会自己去编译&#xff0c;等待一会便好&#xff0c;查看微信开发者工具控制台是否有报错日志 如果发现[插件 w…

Yshop框架的小程序登录

1配置 根据请求头去判断&#xff0c;走小程序&#xff0c;还是Pc端。 #jwt jwt:header: Authorization#小程序前缀 请求头mini-program-header: MiAuthorization# 令牌前缀token-start-with: Bearersecret: k09BQnaF# 必须使用最少88位的Base64对该令牌进行编码base64-secret…