【前端面试】随机、结构赋值、博弈题

news2026/2/12 15:01:33

解构赋值(Destructuring Assignment)是 JavaScript ES6 引入的一项非常有用的特性,它允许我们快速地从数组或对象中提取值,并将它们赋给变量。这种方式使得代码更加简洁、易读,并且能够减少重复的访问和赋值操作。

1. 数组解构赋值

通过解构赋值,我们可以直接从数组中提取值并赋给变量。例如:

// 基本的数组解构赋值
const arr = [1, 2, 3];
const [a, b, c] = arr;

console.log(a); // 1
console.log(b); // 2
console.log(c); // 3

说明

  • abc 分别从数组 arr 中提取了值。
  • 解构赋值顺序是按数组的索引顺序进行的。

跳过元素
如果我们只需要数组中的部分元素,可以跳过不需要的元素:

const arr = [1, 2, 3];
const [a, , c] = arr;  // 跳过第二个元素

console.log(a); // 1
console.log(c); // 3

默认值
解构时,如果数组的某个位置没有值,可以为该变量提供默认值:

const arr = [1];
const [a, b = 2] = arr;

console.log(a); // 1
console.log(b); // 2

2. 对象解构赋值

对象解构赋值允许我们从对象中提取特定的属性并赋给变量。

const person = { name: 'Alice', age: 25 };
const { name, age } = person;

console.log(name); // Alice
console.log(age);  // 25

说明

  • 变量名需要与对象属性的名称相同。如果变量名与对象属性名不同,可以通过 : 来重命名:
const person = { name: 'Alice', age: 25 };
const { name: personName, age: personAge } = person;

console.log(personName); // Alice
console.log(personAge);  // 25

默认值
如果某个属性在对象中不存在,可以为该属性设置默认值:

const person = { name: 'Alice' };
const { name, age = 30 } = person;

console.log(name); // Alice
console.log(age);  // 30

嵌套解构
你还可以对对象进行嵌套解构,从嵌套的对象中提取值:

const person = { name: 'Alice', address: { city: 'Wonderland', zip: '12345' } };
const { name, address: { city, zip } } = person;

console.log(name); // Alice
console.log(city); // Wonderland
console.log(zip);  // 12345

3. 解构赋值与剩余操作符

如果你需要从数组或对象中提取出剩余的元素或属性,可以使用剩余操作符 ...

数组的剩余解构

const arr = [1, 2, 3, 4, 5];
const [first, second, ...rest] = arr;

console.log(first);  // 1
console.log(second); // 2
console.log(rest);   // [3, 4, 5]

对象的剩余解构

const person = { name: 'Alice', age: 25, city: 'Wonderland' };
const { name, ...otherInfo } = person;

console.log(name);     // Alice
console.log(otherInfo); // { age: 25, city: 'Wonderland' }

4. 函数参数中的解构赋值

解构赋值可以与函数参数结合使用,直接从传入的对象或数组中提取值:

数组解构作为函数参数

function sum([a, b]) {
  return a + b;
}

console.log(sum([3, 5])); // 8

对象解构作为函数参数

function greet({ name, age }) {
  console.log(`Hello, ${name}! You are ${age} years old.`);
}

greet({ name: 'Alice', age: 25 }); // Hello, Alice! You are 25 years old.

带默认值的函数参数解构

function greet({ name = 'Guest', age = 18 } = {}) {
  console.log(`Hello, ${name}! You are ${age} years old.`);
}

greet({ name: 'Alice' }); // Hello, Alice! You are 18 years old.
greet(); // Hello, Guest! You are 18 years old.

这段代码 [arr[i], arr[j]] = [arr[j], arr[i]]; 是数组元素交换的语法,属于一种解构赋值的用法。它通常用于交换数组中两个元素的位置。

解释

  1. 解构赋值:这是 JavaScript ES6 中引入的一个特性,允许我们使用数组或对象的结构来进行赋值。

  2. 数组元素交换:在没有解构赋值的语法时,我们通常使用临时变量来交换两个元素,比如:

    let temp = arr[i];
    arr[i] = arr[j];
    arr[j] = temp;
    

    而使用解构赋值的方式可以减少临时变量的使用,使代码更简洁。通过这种方式,arr[i]arr[j] 两个元素的值会交换。

使用场景

这个代码片段在Fisher-Yates 洗牌算法中非常常见,它用于随机打乱数组中的元素顺序。通过不断交换数组中的元素,从最后一个元素开始,逐步将每个元素与之前的元素交换,确保每个元素都有相等的概率出现在数组的任何位置。

示例:Fisher-Yates 洗牌算法实现

function shuffleArray(arr) {
  for (let i = arr.length - 1; i > 0; i--) {
    // 随机选择一个索引 j,其中 0 <= j <= i
    const j = Math.floor(Math.random() * (i + 1));
    // 交换 arr[i] 和 arr[j]
    [arr[i], arr[j]] = [arr[j], arr[i]];
  }
}

const arr = [1, 2, 3, 4, 5];
shuffleArray(arr);
console.log(arr); // 打乱顺序后的数组

这段代码的关键点:

  • Fisher-Yates 洗牌算法:这个算法的核心思想是从数组的最后一个元素开始,随机选择一个元素并与当前元素交换位置,直到整个数组都经过处理。这确保了数组中每个元素出现的顺序是随机的。
  • 解构赋值:通过 [arr[i], arr[j]] = [arr[j], arr[i]]; 来简洁地交换元素,无需使用额外的临时变量。

以下是将上述题目改成先输后赢情况的题目及对应答案,也就是目标变为让对方拿到最后一颗石子、最后一枚硬币等情况来取得胜利,供你参考:

💡题目 1:取石子游戏(先输后赢版)

  • 有一堆石子,共 100 颗。甲、乙两人轮流从中取石子,每次最少取 1 颗,最多取 5 颗。取到最后一颗石子的人输。假设甲先取,问甲有没有必胜策略?如果有,甲第一步应该取几颗石子?

答案:

甲有必胜策略。因为要让乙取到最后一颗石子(即甲要避免取到最后一颗),那就需要保证每轮两人共取 6 颗石子(1 + 5 = 6,2 + 4 = 6,3 + 3 = 6 等情况),使得最后剩下 1 颗留给乙。100÷6 = 16……4,甲先取 4 颗石子,之后乙取 n 颗(1≤n≤5),甲就取 6 - n 颗,这样经过 16 轮后,就会剩下 1 颗石子留给乙去取,乙取到最后这颗石子,甲获胜。

💡题目 2:硬币游戏(先输后赢版)

  • 桌上有 20 枚硬币,A、B 两人轮流拿硬币,每次可以拿 1 到 3 枚。谁拿到最后一枚硬币谁输。假设 A 先拿,A 有没有必胜策略?

答案:

A 有必胜策略。要保证 B 拿到最后一枚硬币,就要使得最后一轮留给 B 时只剩下 1 枚硬币。因为每次两人能取 1 到 3 枚,若想控制每轮取的数量,让两人一轮共取 4 枚硬币(1 + 3 = 4,2 + 2 = 4,3 + 1 = 4)是可行的。20÷4 = 5,没有余数,A 先拿 1 枚硬币,之后 B 拿 n 枚(1≤n≤3),A 就拿 4 - n 枚,这样经过 4 轮后,会剩下 1 枚硬币留给 B 去拿,A 获胜。

💡题目 3:划分数字(先输后赢版)

  • 给定数字 10,A、B 两人轮流进行操作。操作可以是将当前数字减去 1 或者减去 2。谁先将数字减到 0 谁输。假设 A 先操作,A 有没有必胜策略?

答案:

A 有必胜策略。A 要避免自己把数字减到 0,那就需要让 B 去减到 0,所以 A 第一次要将 10 减去 2 变为 8。之后 B 操作,如果 B 减 1,A 就减 2;如果 B 减 2,A 就减 1,保证每轮两人共减去 3。因为 8÷3 = 2……2,经过 2 轮后,数字变为 2,此时不管 B 减 1 还是减 2,A 都能进行相应操作使得最后 B 把数字减到 0,A 获胜。

💡题目 4:报数游戏(先输后赢版)

  • A、B 两人轮流报数,从 1 开始报,每次可以报 1 个或 2 个连续的数。谁报到 20 谁输。假设 A 先报,A 有没有必胜策略?

答案:

A 有必胜策略。A 要避免报到 20,要让 B 报到 20。A 先报 1 个数,报 1。然后 B 报数,如果 B 报 1 个数,A 就报 2 个数;如果 B 报 2 个数,A 就报 1 个数,保证每轮两人共报 3 个数。因为 (20 - 1)÷3 = 6……1,经过 6 轮后,正好轮到 B 报数,此时 B 只能报 20,B 输,A 获胜。

💡题目 5:火柴游戏(先输后赢版)

  • 有 15 根火柴,A、B 两人轮流取火柴,每次可以取 1 根、2 根或 3 根。取到最后一根火柴的人输。假设 A 先取,A 有没有必胜策略?

答案:

A 有必胜策略。A 要让 B 取到最后一根火柴,也就是要保证最后剩下 1 根留给 B。因为每次两人取 1 到 3 根,控制每轮两人共取 4 根火柴(1 + 3 = 4,2 + 2 = 4,3 + 1 = 4)就行。15÷4 = 3……3,A 先取 3 根火柴,剩下 12 根,然后 B 取 n 根(1≤n≤3),A 就取 4 - n 根,这样经过 3 轮后,就会剩下 1 根火柴留给 B 去取,A 获胜。

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

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

相关文章

springboot437校园悬赏任务平台(论文+源码)_kaic

摘 要 使用旧方法对校园悬赏任务平台的信息进行系统化管理已经不再让人们信赖了&#xff0c;把现在的网络信息技术运用在校园悬赏任务平台的管理上面可以解决许多信息管理上面的难题&#xff0c;比如处理数据时间很长&#xff0c;数据存在错误不能及时纠正等问题。这次开发的校…

医学分割数据集白内障严重程度分割数据集labelme格式719张3类别

数据集格式&#xff1a;labelme格式(不包含mask文件&#xff0c;仅仅包含jpg图片和对应的json文件) 图片数量(jpg文件个数)&#xff1a;719 标注数量(json文件个数)&#xff1a;719 标注类别数&#xff1a;3 标注类别名称:["normal","severe","mi…

搭建Tomcat(二)--反射的应用

引入 Tomcat 在处理HTTP请求时&#xff0c;会根据一系列规则和配置来判断该请求是想要获取动态资源还是静态资源。 为什么要对请求进行判断&#xff1f; Tomcat 判断HTTP请求是动态请求还是静态请求的主要目的是确定如何生成并返回响应内容。静态请求通常意味着服务器只需读取并…

电子科技大学考研,计算机与软件专业怎么选择?

电子科技大学在计算机与软件领域具备卓越实力&#xff0c;其毕业生就业前景及薪资水平均颇为可观。因此&#xff0c;学生应依据个人课程专长来选定专业。若各项课程均表现出色&#xff0c;推荐25届考生优先考虑软件专业&#xff0c;因其上岸难度相对较低。 接下来&#xff0c;C…

部署GitLab服务器

文章目录 环境准备GitLab部署GitLab服务器GitLab中主要的概念客户端上传代码到gitlab服务器CI-CD概述软件程序上线流程安装Jenkins服务器 配置jenkins软件版本管理配置jenkins访问gitlab远程仓库下载到子目录部署代码到web服务器自动化部署流程 配置共享服务器配置jenkins把git…

Python中的优化函数2:cvxpy包

文章目录 介绍使用步骤示例1示例2官方文档 介绍 它是一个基于 Python 的凸优化建模工具&#xff0c;专门用于定义和求解 凸优化问题&#xff08;Convex Optimization Problems&#xff09;。CVXPY 提供了一种直观的方式来表达优化问题&#xff0c;并通过高效的求解器来解决这些…

MSciNLI—— 针对科学自然语言推理任务提出的多样化数据集用于训练语言模型和大规模语言模型建立基线

概述 论文地址&#xff1a;https://arxiv.org/pdf/2404.08066 源码地址&#xff1a;https://github.com/msadat3/mscinli 自然语言推理&#xff08;NLI&#xff09;是一项识别两个句子之间语义关系的任务。第一个句子称为 “前提”&#xff0c;第二个句子称为 “假设”。传统的…

REVERSE-COMPETITION-CISCN-2025

REVERSE-COMPETITION-CISCN-2025 rand0mezCskydumpcython rand0m 3.12版本的pyd逆向 读16进制&#xff0c;分成4个4字节的int&#xff0c;每个int做两步运算 第一步&#xff0c;右移28bit&#xff0c;左移4bit&#xff0c;然后拼接 注意左移4bit后又&0x3a3affff&#xff0…

批量合并多个Excel到一个文件

工作中&#xff0c;我们经常需要将多个Excel的数据进行合并&#xff0c;很多插件都可以做这个功能。但是今天我们将介绍一个完全免费的独立软件【非插件】&#xff0c;来更加方便的实现这个功能。 准备Excel 这里我们准备了两张待合并的Excel文件 的卢易表 打开的卢易表软件…

【算法】—— 前缀和

一、区间求和问题 给定一个长度为n的序列a&#xff0c;有m次查询&#xff0c;每次查询输出一个连续区间的和。 使用暴力做法求解是将每次查询都遍历该区间求和 //暴力做法import java.util.Scanner;public class Test {public static void main(String[] args){Scanner scan…

股市投资策略升级:掌握马尔可夫决策过程与强化学习,提升交易技能

作者&#xff1a;老余捞鱼 原创不易&#xff0c;转载请标明出处及原作者。 写在前面的话&#xff1a;本文将深入探讨马尔可夫决策过程&#xff08;MDP&#xff09;和强化学习在股票交易中的运用。通过阐述MDP的基本原理和其在交易策略中的实际应用&#xff0c;试图向您揭示这些…

jvm结构介绍

1. 垃圾回收&#xff08;Garbage Collection, GC&#xff09;&#xff1a;JVM自动管理内存的机制&#xff0c;负责回收不再使用的对象占用的内存空间。常见的垃圾回收算法包括标记-清除&#xff08;Mark-Sweep&#xff09;、复制&#xff08;Copying&#xff09;、标记-整理&am…

基于智能电能表的智能家居能源管理系统设计

目录 引言系统设计 硬件设计软件设计系统功能模块 电能测量模块数据传输模块能源管理模块控制算法 数据采集与处理算法能源优化算法代码实现 电能测量模块实现数据传输模块实现系统调试与优化结论与展望 1. 引言 随着智能家居的发展&#xff0c;电能管理成为智能家居系统中的…

【计算机组成原理】实验二:通用寄存器单元实验

实验二&#xff1a;通用寄存器单元实验 一、实验目的 了解通用寄存器的组成和硬件电路&#xff0c;利用通用寄存器实现数据的置数、左移、右移等功能。 二、实验内容 数据输入通用寄存器 寄存器内容无进位位左移实验 寄存器内容无进位位右移实验 三、实验步骤和结果 实…

codeforces一些题目思路复盘

codeforces round 919 dv2 C Partitioning the Array 大致题意&#xff0c;对于n约数i&#xff0c;我们把原数组分成份&#xff0c;并且每份中有i个元素&#xff0c;对于每个分组情况&#xff0c;如果存在一个数m使得数组中元素modm后使得每个部分的数组完全相同&#xff0c;如…

《拉依达的嵌入式\驱动面试宝典》—C/CPP基础篇(四)

《拉依达的嵌入式\驱动面试宝典》—C/CPP基础篇(四) 你好,我是拉依达。 感谢所有阅读关注我的同学支持,目前博客累计阅读 27w,关注1.5w人。其中博客《最全Linux驱动开发全流程详细解析(持续更新)-CSDN博客》已经是 Linux驱动 相关内容搜索的推荐首位,感谢大家支持。 《拉…

又细又长的马尾:tail

英语里边有一个单词 tail&#xff0c;意为“尾巴”&#xff0c;这应当是众所周知的事情了。 不过&#xff0c;tail 这条尾巴&#xff0c;并不简单&#xff0c;因为它还是一个词根&#xff0c;也就是说 tail 其实是自由词素。 事实上&#xff0c;tail 最初来自 马尾 这样一个概…

Lumos学习王佩丰Excel第二十一讲:经典Excel动态图表实现原理

一、动态图表实现原理 1、理解图表中的数据系列 在Excel图表中&#xff0c;系列指的是图表中的数据集合&#xff0c;它通常代表着一个数据源。每个系列都可以包含多个数据点&#xff0c;这些数据点在图表中以特定的形式展现&#xff0c;如柱状图中的柱子&#xff0c;折线图中…

使用Qt Creator设计可视化窗体(一)

一、创建项目 打开 Qt Creator &#xff0c;在菜单栏中选中&#xff1a; “文件” --------> “新建文件或项目” &#xff1b;或者使用快捷键&#xff1a;Ctrl n&#xff1b;或者直接点击&#xff1a;“new” Qt 中的构建工具有三种可供选择&#xff0c;分别是&#…

Rust之抽空学习系列(四)—— 编程通用概念(下)

Rust之抽空学习系列&#xff08;四&#xff09;—— 编程通用概念&#xff08;下&#xff09; 1、函数 函数用来对功能逻辑进行封装&#xff0c;能够增强复用、提高代码的可读 以下是函数的主要组成部分&#xff1a; 名称参数返回类型函数体 1.1、函数名称 在Rust中&…