软考:软件设计师 — 15.数据结构及算法应用

news2024/10/1 21:42:30

十五. 数据结构及算法应用

数据结构及算法应用类题目是下午场考试中的第四道题目,分值 15 分,主要以 C 语言填空、算法策略判断和时间复杂度判断为考察形式,建议拿到 6 分以上。

1. 解题技巧

算法策略与时间复杂度部分详细内容可以参考文章:软考:软件设计师 — 14.算法基础

(1)算法策略区分

  • 分治法(主要是二分)

特征:把一个问题拆分成多个小规模的相同子问题,一般可用递归解决。

经典问题:斐波那契数列、归并排序、快速排序、二分搜索、矩阵乘法、大整数乘法等

  • 贪心法(一般用于求满意解)

特征:局部最优,但整体不见得最优。每步有明确的、既定的策略。

经典问题:背包问题(如装箱)、多机调度、找零钱问题

  • 动态规划法(用于求最优解)

特征:划分子问题,并把子问题结果适用数组存储,利用查询子问题结果构造最终问题结果。(一般自顶向下时间复杂度为 O(2^{n}),自底向上时间复杂度为 O(n^{a}),后者效率更高)

经典问题:斐波那契数列、矩阵乘法、背包问题、LCS最长公共子序列

  • 回溯法

特征:系统搜索一个问题的所有解或任一解。

经典问题:N皇后问题、迷宫、背包问题

算法名称

关键点

特征

典型问题

分治法递归技术把一个问题拆分成多个小规模的相同子问题,一般可用递归解决。归并排序、快速排序、二分搜索
贪心法一般用于求满意解,特殊情况可求最优解(部分背包)局部最优,但整体不一定最优。每步有明确的、既定的策略。背包问题(如装箱)、多机调度、找零钱问题
动态规划法最优子结构和递归式划分子问题(最优子结构),并把子问题结果使用数组存储,利用查询子问题结果构造最终问题结果。矩阵乘法、背包问题、LCS最长公共子序列
回溯法探索和回退系统搜索一个问题的所有解或任一解。有试探和回退的过程。N皇后问题、迷宫、背包问题

算法策略判断:

  • 回溯:有尝试探索和回退的过程。
  • 分治:分治和动态规划比较难区分。分治不好解决问题,从而记录中间解解决问题。分治主要采用二分的思想,二分以外都用动态规划法解决了。二分的时间复杂度与 O(nlog2n) 相关,需注意有无外层嵌套循环,如果有,则需要再乘 n。(结合归并排序、快速排序的过程,也是二分的)
  • 动态规划法:有递归式,自底向上实现时,中间解基本上查表可得,时间复杂度一般是 O(n^{a}),具体 a 的值取决于 for 循环的嵌套层数。如果循环变量从 0 或 1 开始,到 n 结束,这种情况就是从小规模到大规模,自底向上。如果自顶向下,时间复杂度为 O(2^{n}),和分治的实现就差不多了,查表的意义可以忽略不记,循环变量一般由 n 开始,向 1 缩小,是从大规模到小规模。
  • 贪心法:有时也会出现最优子结构的描述,但没有递归式。考虑的是当前最优,求得的是满意解。

(2)时间复杂度与空间复杂度

常见的对算法执行所需时间的度量:

O(1)<O(log_{2}n)<O(n)<O(nlog_{2}n)<O(n^{2})<O(n^{3})<O(2^{n})

(3)代码填空技巧

仔细审题:

  • 检查所有用到的变量是否有声明,是否赋初值;
  • 检查是否有返回值,与题干要求返回变量名或上下文是否一致;
  • 检查 for 循环是否有计数变量的赋值、初值和终止条件;
  • 注意 while 循环的开始和结束;
  • 有一些变量名具有特殊含义,比如一般用 max/min 保存最大值/最小值,temp 作为中间变量,一般用来存储中间值或用来做数值交换的中间过渡。x>max,则修正 max=x;x<min,则修正 min=x;
  • 对特殊的算法策略:回溯法是否有回退 k=k-1;分治法递归的递归调用(调用自身函数名);动态规划法的查表操作;
  • 注意题干描述和代码说明、递归式(条件和等式)、代码中的注释、代码上下文。一般特殊数据结构调用方式会在代码说明或代码上下文中给出。
  1. 题干公式很重要,一般公式体现在代码中,会有循环边界、判断条件等;
  2. 代码说明很重要,一般代码说明会指出一些变量的定义、初始值和边界值;
  3. 代码上下文很重要,可以根据上下文判断有没有缺失变量声明、变量赋值;
  4. 题干说明很重要,题干有时候会给出循环边界、判断条件等内容。还可以根据题干描述,判断使用的算法策略,不同的算法策略,一般会有一些典型的代码缺失,比如:动态规划法可能会考察题干给出的递归式以及最优解的判断;分治法一般会考察递归式以及问题的划分;贪心法一般会考察满意解的当前最优判断条件;回溯法一般会考察回退的过程。

2. 例题

(1)背包问题介绍

有 n 物品,第 i 个物品价值为 v_{i},重量为 w_{i},其中 v_{i} 和 w_{i} 均为非负数,背包的容量为 W,W 为非负数。现需要考虑如何选择装入背包的物品,使装入背包的物品总价值最大。

部分背包问题(物品可分割)

这类问题通常可以通过依次选择单位价值(v_{i}/w_{i})最大的物品进行放入,剩余体积不够时,进行切割,从而得到最优结果。

0-1 背包问题(物品不可分割)

形式化描述如下:

目标函数为 max\sum_{i=1}^{n}v_{i}x_{i}

约束条件为 \sum_{i=1}^{n}w_{i}x_{i}\leq W,x_{i}\in {0,1}

满足约束条件的任一集合 (x_{1},x_{2},\cdots ,x_{n}) 是问题的一个可行解。

放置策略

可以将背包问题的求解过程看作是进行一系列决策的过程,即决定哪些物品应该放入背包,哪些物品不放入背包。

  • 优先放体积最大,超过背包体积则放弃其它物品(5,4;30);
  • 优先放价值最大,超过背包体积则放弃其它物品(5,4;30);
  • 优先放单位价值最大,超过背包体积则放弃其它物品(5,3;29);
  • 按顺序放置,不合适就退出来重新放置,直到尝试完背包能够放置的所有方案;
  • 刻画 0-1 背包问题的最优解的结构:

如果一个问题的最优解包含了物品 n,即 x_{n}=1,那么其余 x_{1},x_{2},\cdots ,x_{n-1} 一定构成子问题 1,2,…,n-1 在容量 W-w_{n} 的最优解。如果这个最优解不包含物品 n,即 x_{n}=0,那么其余 x_{1},x_{2},\cdots ,x_{n-1} 一定构成子问题 1,2,…,n-1 在容量 W 的最优解。

如果题目中有对最优子结构的描述,用贪心法可以求得最优解(参考贪心法求解部分背包问题)。

(2)背包问题 - 贪心法

说明:

设有 n 个货物要装入若干个容量为 C 的集装箱以便运输,这 n 个货物的体积分别为 {S_{1},S_{2},\cdots ,S_{n}},且有 S_{i} ≤ C(1≤i≤n)。为节省运输成本,用尽可能少的集装箱来装运这 n 个货物。

下面分别采用最先适宜策略和最优适宜策略来求解该问题。

最先适宜策略首先将所有的集装箱初始化为空,对于所有货物,按照所给的次序,每次将一个货物装入第一个能容纳它的集装箱中。

最优适宜策略与最先适宜策略类似,不同的是,总是把货物装到能容纳它且目前剩余容量最小的集装箱,使得该箱子装入货物后闲置空间最小。

C代码:

变量说明

n:货物数

C:集装箱容量

s:数组,长度为 n,其中每个元素表示货物的体积,下标从 0 开始

b:数组,长度为 m,b[i] 表示第 i+1 个集装箱当前已经装入货物的体积,下标从 0 开始

i,j:循环变量

k:当前所用的集装箱数量

min:集装箱装入了第 i 个货物后的最小剩余容量

m:当前所需要的集装箱数量

temp:临时变量

具体代码

(1)最先适宜策略

/* 最先适宜策略首先将所有的集装箱初始化为空,对于所有货物,
按照所给的次序,每次将一个货物装入第一个能容纳它的集装箱中 */

int firstfit(){
  int i,j;
  k=0;
  for(i=0; i<n; i++){
   b[i]=0;
  }
  for(i=0; i<n; i++){
  (1);
   while(C-b[i]<s[i]){
    j++;
   }
  (2);
  k=k>(j+1)?k:(j+1);
  }
  return k;
}

(2)最优适宜策略

/* 最优适宜策略与最先适宜策略类型,不同的是,
总是把货物装到能容纳它且目前剩余容量最小的集装箱中,使得该箱子装入货物后闲置空间最小。*/

int bestfit(){
  int i,j,min,m,temp;
  k=0;
  for(i=0; i<n; i++){
  b[i]=0;
  }
  for(i=0; i<n; i++){
   min=C;
   m=k+1;
   for(j=0; j<k+1; j++){
     temp=C-b[i]-s[i];
     if(temp>0&&temp<min){
       (3);
       m=j;
     }
   }
   (4);
   k=k>(m+1)?k:(m+1);
  }
  return k;
} 

问题1:

根据说明和 C 代码,填充 C 代码中的空(1)~(4);

问题2:

根据说明和 C 代码,该问题在最先适宜和最优适宜策略下分别采用了(5)和(6)算法设计策略,时间复杂度分别为(7)和(8)。

问题3:

考虑实例 n=10,C=10,各个货物的体积为 {4,2,7,3,5,4,2,3,6,2}。该实例在最先适宜和最优适宜策略下所需的集装箱数分别为(9)和(10)。考虑一般的情况,这两种求解策略能否确保得到最优解?(11)(能或否)

解析1:

在最先适宜策略代码中,第一个 for 循环中首先初始化了每个集装箱中装入货物的体积,第二个 for 循环中,有 while 循环去判断剩余集装箱的体积与每个货物的体积情况,货物体积大于集装箱剩余体积,则 j++,进入下一个集装箱。每个变量使用前都需要初始化,变量 j 没有初始化,因此第(1)空处填写初始化 j 变量的操作,即 j=0。如果货物体积不大于集装箱剩余体积,那么就说明可以放入集装箱中,因此第(2)处缺失的是装箱的操作,即 b[i] = b[i] + s[i]。

在最优适宜策略代码中,第一个 for 循环中首先初始化了每个集装箱中装入货物的体积,第二个 for 循环中,首先将集装箱容量初始化为最小,因为一开始集装箱中没装任何货物,也是最小剩余容量,m 代表当前所需要的集装箱数量或者集装箱的编号,因为初始编号从 0 开始,嵌套的 for 循环去遍历目前用到的集装箱,因为货物要放入能容纳它并且目前集装箱容量最小的那个,使用 temp 存储目前各集装箱的剩余容量,如果 temp 大于 0 (合法)并且比当前最小值要小的话,说明此时的最小值应该是 temp,找到当前剩余容量最小的集装箱,同时把遍历的第几个集装箱赋值给 m,那么此时的最小值是temp,即 min = temp;下一步缺少的也是装箱操作,注意此时不再是 b[j],而是 b[m],b[m] 才是目前剩余容量最小的集装箱,即 b[m] = b[m] + s[i]。

(1)j=0 (2)b[j] = b[j] + s[i](3)min = temp (4)b[m] = b[m] + s[i]

解析2:

最先适宜策略是将货物装到第一个能容纳它的集装箱中,考虑的是局部最优,即贪心策略;最优适宜策略虽然有最优的概念,但是将货物装入能容纳它且目前剩余容量最小的箱子中,考虑的也是局部最优,即贪心策略。根据它们的 C 代码,最先适宜策略中涉及到两个平行的 for 循环以及一个嵌套进第二个 for 循环的 while 循环,有两层遍历,一层是遍历货物 n,一层是判断货物的体积与集装箱剩余的体积,因此时间复杂度为 O(n^{2});最优适宜策略中涉及到了两层嵌套的 for 循环,一层是遍历货物,一层是遍历集装箱,因此时间复杂度为 O(n^{2})。

(5)贪心 (6)贪心 (7)O(n^{2}) (8)O(n^{2})

解析3:

具体实例的判断可通过画图或者推理得出,最先适宜策略是放入第一个能容纳当前货物的集装箱中,最优适宜策略是放入能容纳当前货物且目前剩余容量最小的集装箱中:

由图示可得,最先适宜策略需要 5 个集装箱,最优适宜策略需要 4 个集装箱;因此这两种策略不能确保得到最优解。 

后续会持续更新整理。

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

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

相关文章

测试干货 | 如何选择合适的半导体检测方法?看完这篇就明白了!

撰文排版&#xff1a;刘佳 审核指导&#xff1a;肖俊灵 本文较长&#xff0c;建议先收藏后随时查看&#xff01;以后我们将更新更多此类硬核科普&#xff0c;欢迎关注&#xff01; 半导体材料作为半导体产业链中的重要支撑&#xff0c;包括以硅、锗等为代表的元素半导体材料和以…

图与树的基本概念

目录 引言 图与树结构的重要性 图的基本概念 图的表示方式 图的遍历算法 树的基本概念 树的定义与性质 树的遍历 二叉树与多叉树的概念 图与树的高级应用 最短路径算法 最小生成树算法 总结与应用 综合实例分析 引言 在计算机科学的世界中&#xff0c;图和树是两…

商圈停车泊位实时查询与推荐系统 项目编号:17259(案例分享)

摘 要 在当今城市化进程加快的背景下&#xff0c;城市停车问题日益突出&#xff0c;给市民出行带来诸多不便。为解决停车难题&#xff0c;提高停车效率&#xff0c;基于Java开发语言和Spring Boot框架&#xff0c;结合MySQL数据库技术&#xff0c;开发了商圈停车泊位实时查询…

计算机Java项目|基于SpringBoot的网络海鲜市场系统的设计与实现

作者主页&#xff1a;编程指南针 作者简介&#xff1a;Java领域优质创作者、CSDN博客专家 、CSDN内容合伙人、掘金特邀作者、阿里云博客专家、51CTO特邀作者、多年架构师设计经验、多年校企合作经验&#xff0c;被多个学校常年聘为校外企业导师&#xff0c;指导学生毕业设计并参…

牛客小白月赛96

牛客小白月赛96 A 最少胜利题数 链接&#xff1a;https://ac.nowcoder.com/acm/contest/84528/A 来源&#xff1a;牛客网 题目描述 本场小白月赛共 6 题&#xff0c;&#x1d435;&#x1d456;&#x1d45b;&#x1d454;&#x1d44f;&#x1d45c;&#x1d45b;&#x1d4…

【hot100篇-python刷题记录】【找到字符串中所有字母异位词】

R6-滑动窗口篇 印象题 核心&#xff1a; 使用collections方法的Counter计数&#xff0c;统计了某个子串中每个字母出现的次数。 判断子串相等&#xff1a;counter1counter2 &#xff08;注意&#xff1a;此时&#xff0c;counter1或者counter2都不能含有多余的项&#xff0…

JVM系列--初始JVM

根据《黑马程序员JVM虚拟机入门到实战全套视频教程》整理 1 什么是JVM JVM 全称是 Java Virtual Machine&#xff0c;中文译名 Java虚拟机。JVM 本质上是一个运行在计算机上的程序&#xff0c;他的职责是运行Java字节码文件。 Java源代码执行流程如下&#xff1a; 分为三个步…

Mysql 集群技术

一、Mysql 在服务器中的部署方法 在企业中90%的服务器操作系统均为Linux在企业中对于Mysql的安装通常用源码编译的方式来进行官网&#xff1a;http://www.mysql.com 1.1 在Linux下部署mysql cmake \ -DCMAKE_INSTALL_PREFIX/usr/local/mysql \ #指定安装路径 -DMYSQL_DATADI…

【Unity变现】Unity 接入Unity ADS广告

说在前面的话&#xff0c;Unity ADS是Unity官方做的广告变现平台&#xff0c;但广告在我国大陆无法使用&#xff0c;开发时测试的话需要上代理才能看到请求的广告。 如果游戏不准备发布到海外市场&#xff0c;可以不考虑这个平台。 一、注册Unity ADS平台的准备 https://dash…

JavaEE 第17节 网络通信知识扫盲

文章目录 前言一、网络通信的概念二、局域网&广域网 局域网&#xff08;LAN&#xff0c;Local Area Network&#xff09; 广域网 三、IP地址与端口号 1、IP地址 2、端口号 四、网络协议 1、概念&作用 2、协议分层&#xff08;重要&#xff09; 前言 此篇博…

你是如何更精准地指引模型,激发其无尽的创造力?

随着大型语言模型日益凸显其重要性&#xff0c;发掘并充分利用它们的潜力&#xff0c;很大程度上依赖于我们如何巧妙构思和构造指令——即Prompt的精炼艺术。优化Prompt撰写技巧&#xff0c;将能够更好地引导大模型&#xff0c;为各类应用场景生成高质量的文本输出。分享出你的…

CTF杂项题:easy_nbt writeup

题目 题目如图&#xff0c;有一个附件&#xff1a;file.7z 解题思路 CTF的杂项题&#xff0c;对于刚接触的人员来说&#xff0c;很多时候是完全没有思路&#xff0c;解这类题&#xff0c;没有相关知识储备的时候&#xff0c;可以使用文件内容搜索工具搜索flag、ctf、key等关键…

【实现100个unity特效之25】Unity中实现二次元模型,基于光照的内置和URP管线卡通化渲染shader

最终效果 文章目录 最终效果默认效果简单粗暴&#xff0c;使用Unlit/Texture基于光照模型的卡通渲染UnityToonShader——仅支持内置渲染管线基于光照模型的二次元渲染UnityURPToonLitShaderExample——仅支持URP渲染管线 完结 默认效果 不然不做处理&#xff0c;我们的模型默认…

高并发eleme项目登录模块(thirty-three day)

一、配置一主二从mysql 1. mycat对mysql8不完全支持 2. mysql8主从问题不大get_pub_key1 3. gtids事务复制 4. 删除/etc/my.cnf 5. 同步data文件需要先停用mysql服务,删除data目录中的auto.cnf 6. gtid模式以及经典模式都需要锁表 flush tables with read lock; unlock …

怎么用电脑兼职赚钱,普通人可做的6个副业项目(非常详细)零基础入门到精通,收藏这篇就够了

现在的生活中&#xff0c;我们总是感觉所过的日子都很紧张&#xff0c;虽然我们尽可能地工作和努力&#xff0c;但是生活成本和社会压力仍然那么大。为了弥补自己的生活经验和财务困难&#xff0c;很多人开始寻找一种额外的收入来源。 其实这种额外的收入来源就被称之为&#…

google paly修改地区教程【2024自测可用】

【准备信息】 https://usfakename.com/ &#xff1a; 用来生成其他国家&#xff08;比如美国&#xff09;的地址 重要需要填写的内容&#xff1a; 卡号&#xff1a;4532 7875 1109 8437 City:Boulder State:Alabama postcode:35259 可以在美国邮政编码ZIP Code(转载) -…

学习yolo+Java+opencv简单案例(一)

目录 一、大概架构 二、编写pom.xml 1、yolo-study模块&#xff08;root&#xff09;&#xff1a; 2、CameraDetection模块 三、编写yml配置文件 四、编写controller 五&#xff0c;可能会出现的问题 1、修改VM启动参数&#xff1a; 2、修改启动类 六、测试 七&…

gradio如何实现修改代码后自动重载运行

使用自动重载加速开发 前提条件&#xff1a;本指南要求你了解 Blocks。在阅读本指南之前&#xff0c;请确保你已经阅读了Blocks指南。 本指南涵盖自动重载、在Python IDE中的重载&#xff0c;以及在Jupyter Notebooks中使用Gradio。 为什么需要自动重载&#xff1f; 当你使…

C#归并排序算法

前言 归并排序是一种常见的排序算法&#xff0c;它采用分治法的思想&#xff0c;在排序过程中不断将待排序序列分割成更小的子序列&#xff0c;直到每个子序列中只剩下一个元素&#xff0c;然后将这些子序列两两合并并排序&#xff0c;最终得到一个有序的序列。 归并排序实现原…

蓝牙芯片 vs. 蓝牙模块:如何为蓝牙方案做出最佳选择?

不论您是设计全新的低功耗蓝牙产品&#xff0c;还是升级现有产品&#xff0c;开发者都面临的一个关键的选择&#xff1a;是采用蓝牙芯片还是蓝牙模块呢&#xff1f;作为蓝牙技术领域的资深专家&#xff0c;信驰达将从蓝牙芯片与蓝牙模块的各自优缺点进行分析&#xff0c;帮助您…