一道特殊的排序面试题(交换思想活学活用)

2024-05-09 22:18

本文主要是介绍一道特殊的排序面试题(交换思想活学活用),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

如字符串abcdefg,现在需要按索引顺序1、4、2、0、5、3、6重排序,如对于、4、2、0、5、3、6,排序结果为becafdg


面试中很可能遇到这种非常突兀的问题,这需要基础概念牢固到能够随时运用的地步,本题就是一个锻炼


遇到这种题,步骤:在纸上画心里思考,尽力找出一种较为简单的规律,能够正确完成这样的变化要求!

算法题,一部分是考察数据结构掌握,另一部分就是看逻辑思维,随便过来一个问题,能不能分析出规律,能不能找到靠谱的方法,能不能转化为解决问题的代码!

像二叉树也好,链表数组栈队列也好,字符串也好,图也好,本身数据结构组成和原理就是那些,包括排序查找的常规套路就是那些,但是仅仅“理解了”、“背下来了”、“会了”,但运用很差,甚至代码还处于漏洞百出,那么,不仅并不足以通过高难度面试,而且更不足以完成更有挑战难度的工作

如本题,在纸上画个简单的例子,如:

自己假设abcde按1、2、4、0、3变化,如以第一个字符为“当前”字符,暂存其值a,不断的修改为新值,直到最后某个地方,它需要填充新值a时,结束,可不可以呢?在纸上试试

第1步:bbcde,当前为a,a要跳到1,替换a为原串第1个字符b,

第2步:bccde,当前为b,b要跳到2,替换b为原串第2个字符c

第3步:bcede,当前为c,c要跳到4,替换c为原串第4个字符e

第4步:bcedd,当前为e,e要跳到3,替换c为原串第3个字符d

第5步:bcead,当前为d,d要跳到0,替换c为原串第0个字符a,a就是第一个暂存的字符,直接替换掉结束,结果为:bcead,正确,时间复杂度O(N)


ok,纸上找到了正确的思路,然后就是思路转化为代码,用一个变量代表当前所在索引,再用一个变量代表下一步跳到哪里,用一个字符变量暂存第一个字符,

每跳一次前更新当前所在索引的新值,然后更新当前索引和下一步跳的索引


注意代码中main中大片部分是为了生成一个[0, N-1]范围内的不重复的随机序列(如[0, 7-1]范围内的“、4、2、0、5、3、6”)

代码:

#include <iostream>
#include <string>
#include <random>void sort_by_turn (const std::string &str, int *turn) {std::string res = str;if (!turn || str == "") {return;}size_t idx = 0, next = turn[idx], firstidx = idx;char flag = res[idx];do {res[idx] = res[next];idx = next;next = turn[idx];} while (firstidx != next);res[idx] = flag;std::cout << "result: " << res << std::endl;return;
}int main () {std::string str = "abcdefg";int raw[str.length()];int turn[str.length()];for (int i = 0; i < str.length(); i++) {raw[i] = i;}std::random_device rd;for (int i = 0; i < str.length(); i++) {int num;if (i < str.length() - 1) {int idx = rd() % (str.length() - 1 - i);int num = raw[idx + i];turn[i] = num;int t = raw[i];raw[i] = num;raw[i + idx] = t;} else {turn[i] = raw[i];}}for (int i = 0; i < str.length(); i++) {std::cout << turn[i] << "\t";}std::cout << std::endl;sort_by_turn(str, turn);return 0;
}


这篇关于一道特殊的排序面试题(交换思想活学活用)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/974654

相关文章

java不依赖临时变量交换两个变量的值

java不依赖临时变量交换两个变量的值 1.简单易懂的实现方式     int a=1,b=2;     int temp = 0;     temp = a;     a = b;     b= temp; 2.算术算法 int a=1,b=2; a = a+b;// a = 1+2  b = a-b;// b = a-b --> b=3-2 -->1 a = a -b;/

Java比较和交换示例 - CAS算法

Java比较和交换示例 - CAS算法 由Lokesh Gupta | 提起下:多线程 一个Java 5中最好添加的是支持类,如原子操作AtomicInteger,AtomicLong等等。这些课程帮助您最大限度地减少复杂的(非必要)需要多线程的,如增加一些基本的操作代码或递减的值在多个线程之间共享。这些类内部依赖于名为CAS(比较和交换)的算法。在本文中,我将详细讨论这个概念。 1.乐观和

Redis利用zset数据结构如何实现多字段排序,score的调整(finalScore = score*MAX_NAME_VALUE + getIntRepresentation(name) )

1、原文:   2、使用sql很容易实现多字段的排序功能,比如: select * from user order by score desc,name desc; 3、问题:用两个字段(score,name)排序。在redis中应该怎么做?   4、使用按分数排序的redis集合。你必须根据你的需要准备分数。 finalScore = score*MAX_NAME_VALUE +

MySql删除重复数据只保留最小id的那条数据。某某公司的临时面试题

错误代码: DELETE FROMpayment WHEREserial IN ( SELECT serial FROM payment GROUP BY serial HAVING count(*) > 1 ) AND id NOT IN ( SELECT min( id ) AS id FROM payment GROUP BY serial HAVING count( serial )

mysql升序排序使null结果排最后

1.现象mysql升序排序的null结果排最前面   select * FROM payment ORDER BY serial ASC; -- null值最前面  结果: 2.现象mysql降序序排序的null结果排最后面 select * FROM payment ORDER BY serial DESC; -- NULL 值最后 结果:  3.使mysql升序排序的n

2014年5月整理java笔试题及几个小面试题

实现2/1 3/2 5/3 8/5 13/8...前20项的和public class Test {public double sum(){double m = 1; //分母double n = 2;//分子double sum = 0;for (int i = 0; i < 20; i++) {sum = sum+n/m;double temp = m;m = n;n = m + temp;

2014年5月整理java面试题

1.Overload(方法重载)和override(方法覆盖)的区别: overload是指函数的名称相同,但是属性不同(返回类型除外)  override是对父类的虚函数进行“个性化”,要求属性必须与父类中声明的一致,不然会变成overload!   overload是完全隐藏了父类中函数的实现,相当于定义了一个同名函数  override是继承父类中函数实现,同时增加自己的功能

MySQL使用SELECT 语句不加ORDER BY默认是如何排序的?

大家好,我是阿飞云 怕什么真理无穷,进一步有近一步的欢喜 记录一个MySQL查询排序的问题,一个SQL语句没有加order by,那么查询出来的结果到底是按照什么规则排序的呢?查询了网上的一些资料,分享如下: •MyISAM 表 MySQL Select 默认排序是按照物理存储顺序显示的(不进行额外排序)。也就是说SELECT * FROM tbl – 会产生“表扫描”。如果表没有删除、替换、更

sort常用排序模式---------shell基础篇(三)

sort 排序命令使用 表达式意义sort -c test测试文件“test”是否已经经过排序,一般用处不大sort -k1 test.txt按照第1域对文件test.txt进行排序,日常可以用来对合并的日志文件进行时间排序sort -k1 -m log1.txt log2.txt按照第一域进行排序后合并输出到控制台,建议使用“>>” 将合并内容输出到另一个文件中sort -t / -k3 te

二叉树遍历(思想)

根据一棵树的先序/中序遍历,或者后序/中序遍历序列,都可以唯一地确定一棵树,算法如下: 首先根据前序遍历或后序遍历的第一个或最后一个为根结点根据根节点可以在中序遍历中分出左子树部分和右子树部分根据前序/后序遍历的其他节点及中序遍历的左右两部分重复上述两步骤即可 遍历二叉树是以一定规则将二叉树中的结点排列成一个线性序列,得到二叉树中结点的先序序列、中序序列或后续序列。这实质上是对一个非线性结