虽说我们很多时候前端很少有机会接触到算法。大多都交互性的操作,然而从各大公司面试来看,算法依旧是考察的一方面。实际上学习数据结构与算法对于工程师去理解和分析问题都是有帮助的。如果将来当我们面对较为复杂的问题,这些基础知识的积累可以帮助我们更好的优化解决思路。下面罗列在前端面试中经常撞见的几个问题吧。

Q1 判断一个单词是否是回文?

回文是指把相同的词汇或句子,在下文中调换位置或颠倒过来,产生首尾回环的情趣,叫做回文,也叫回环。比如 mamam redivider .

很多人拿到这样的题目非常容易想到用for 将字符串颠倒字母顺序然后匹配就行了。其实重要的考察的就是对于reverse的实现。其实我们可以利用现成的函数,将字符串转换成数组,这个思路很重要,我们可以拥有更多的自由度去进行字符串的一些操作。

function checkPalindrom(str) {

return str == str.split('').reverse().join('');

}

Q2 去掉一组整型数组重复的值

比如输入: [1,13,24,11,11,14,1,2]

输出: [1,13,24,11,14,2]

需要去掉重复的11 和 1 这两个元素。

这道问题出现在诸多的前端面试题中,主要考察个人对Object的使用,利用key来进行筛选。

/**

* unique an array

**/

let unique = function(arr) {

let hashTable = {};

let data = [];

for(let i=0,l=arr.length;i

if(!hashTable[arr[i]]) {

hashTable[arr[i]] = true;

data.push(arr[i]);

}

}

return data

}

module.exports = unique;

Q3 统计一个字符串出现最多的字母

给出一段英文连续的英文字符窜,找出重复出现次数最多的字母

输入 : afjghdfraaaasdenas

输出 : a

前面出现过去重的算法,这里需要是统计重复次数。

function findMaxDuplicateChar(str) {

if(str.length == 1) {

return str;

}

let charObj = {};

for(let i=0;i

if(!charObj[str.charAt(i)]) {

charObj[str.charAt(i)] = 1;

}else{

charObj[str.charAt(i)] += 1;

}

}

let maxChar = '',

maxValue = 1;

for(var k in charObj) {

if(charObj[k] >= maxValue) {

maxChar = k;

maxValue = charObj[k];

}

}

return maxChar;

}

module.exports = findMaxDuplicateChar;

Q4 排序算法

如果抽到算法题目的话,应该大多都是比较开放的题目,不限定算法的实现,但是一定要求掌握其中的几种,所以冒泡排序,这种较为基础并且便于理解记忆的算法一定需要熟记于心。冒泡排序算法就是依次比较大小,小的的大的进行位置上的交换。

function bubbleSort(arr) {

for(let i = 0,l=arr.length;i

for(let j = i+1;j

if(arr[i]>arr[j]) {

let tem = arr[i];

arr[i] = arr[j];

arr[j] = tem;

}

}

}

return arr;

}

module.exports = bubbleSort;

除了冒泡排序外,其实还有很多诸如 插入排序,快速排序,希尔排序等。每一种排序算法都有各自的特点。全部掌握也不需要,但是心底一定要熟悉几种算法。 比如快速排序,其效率很高,而其基本原理如图(来自wiki):

算法参考某个元素值,将小于它的值,放到左数组中,大于它的值的元素就放到右数组中,然后递归进行上一次左右数组的操作,返回合并的数组就是已经排好顺序的数组了。

function quickSort(arr) {

if(arr.length<=1) {

return arr;

}

let leftArr = [];

let rightArr = [];

let q = arr[0];

for(let i = 1,l=arr.length; i

if(arr[i]>q) {

rightArr.push(arr[i]);

}else{

leftArr.push(arr[i]);

}

}

return [].concat(quickSort(leftArr),[q],quickSort(rightArr));

}

module.exports = quickSort;

安利大家一个学习的地址,通过动画演示算法的实现。

Q5 不借助临时变量,进行两个整数的交换

输入 a = 2, b = 4 输出 a = 4, b =2

这种问题非常巧妙,需要大家跳出惯有的思维,利用 a , b进行置换。

主要是利用 + - 去进行运算,类似 a = a + ( b - a) 实际上等同于最后 的 a = b;

function swap(a , b) {

b = b - a;

a = a + b;

b = a - b;

return [a,b];

}

module.exports = swap;

Q6 使用canvas 绘制一个有限度的斐波那契数列的曲线?

数列长度限定在9.

斐波那契数列,又称黄金分割数列,指的是这样一个数列:0、1、1、2、3、5、8、13、21、34、……在数学上,斐波纳契数列主要考察递归的调用。我们一般都知道定义

fibo[i] = fibo[i-1]+fibo[i-2];

生成斐波那契数组的方法

function getFibonacci(n) {

var fibarr = [];

var i = 0;

while(i

if(i<=1) {

fibarr.push(i);

}else{

fibarr.push(fibarr[i-1] + fibarr[i-2])

}

i++;

}

return fibarr;

}

剩余的工作就是利用canvas arc方法进行曲线绘制了

Q7 找出下列正数组的最大差值比如:

输入 [10,5,11,7,8,9]

输出 6

这是通过一道题目去测试对于基本的数组的最大值的查找,很明显我们知道,最大差值肯定是一个数组中最大值与最小值的差。

function getMaxProfit(arr) {

var minPrice = arr[0];

var maxProfit = 0;

for (var i = 0; i < arr.length; i++) {

var currentPrice = arr[i];

minPrice = Math.min(minPrice, currentPrice);

var potentialProfit = currentPrice - minPrice;

maxProfit = Math.max(maxProfit, potentialProfit);

}

return maxProfit;

}

Q8 随机生成指定长度的字符串

实现一个算法,随机生成指制定长度的字符窜。

比如给定 长度 8 输出 4ldkfg9j

function randomString(n) {

let str = 'abcdefghijklmnopqrstuvwxyz9876543210';

let tmp = '',

i = 0,

l = str.length;

for (i = 0; i < n; i++) {

tmp += str.charAt(Math.floor(Math.random() * l));

}

return tmp;

}

module.exports = randomString;

Q9 实现类似getElementsByClassName 的功能

自己实现一个函数,查找某个DOM节点下面的包含某个class的所有DOM节点?不允许使用原生提供的 getElementsByClassName querySelectorAll 等原生提供DOM查找函数。

function queryClassName(node, name) {

var starts = '(^|[ \n\r\t\f])',

ends = '([ \n\r\t\f]|$)';

var array = [],

regex = new RegExp(starts + name + ends),

elements = node.getElementsByTagName("*"),

length = elements.length,

i = 0,

element;

while (i < length) {

element = elements[i];

if (regex.test(element.className)) {

array.push(element);

}

i += 1;

}

return array;

}

Q10 使用JS 实现二叉查找树(Binary Search Tree)

一般叫全部写完的概率比较少,但是重点考察你对它的理解和一些基本特点的实现。 二叉查找树,也称二叉搜索树、有序二叉树(英语:ordered binary tree)是指一棵空树或者具有下列性质的二叉树:

任意节点的左子树不空,则左子树上所有结点的值均小于它的根结点的值;

任意节点的右子树不空,则右子树上所有结点的值均大于它的根结点的值;

任意节点的左、右子树也分别为二叉查找树;

没有键值相等的节点。二叉查找树相比于其他数据结构的优势在于查找、插入的时间复杂度较低。为O(log n)。二叉查找树是基础性数据结构,用于构建更为抽象的数据结构,如集合、multiset、关联数组等。

在写的时候需要足够理解二叉搜素树的特点,需要先设定好每个节点的数据结构

class Node {

constructor(data, left, right) {

this.data = data;

this.left = left;

this.right = right;

}

}

树是有节点构成,由根节点逐渐延生到各个子节点,因此它具备基本的结构就是具备一个根节点,具备添加,查找和删除节点的方法.

class BinarySearchTree {

constructor() {

this.root = null;

}

insert(data) {

let n = new Node(data, null, null);

if (!this.root) {

return this.root = n;

}

let currentNode = this.root;

let parent = null;

while (1) {

parent = currentNode;

if (data < currentNode.data) {

currentNode = currentNode.left;

if (currentNode === null) {

parent.left = n;

break;

}

} else {

currentNode = currentNode.right;

if (currentNode === null) {

parent.right = n;

break;

}

}

}

}

remove(data) {

this.root = this.removeNode(this.root, data)

}

removeNode(node, data) {

if (node == null) {

return null;

}

if (data == node.data) {

// no children node

if (node.left == null && node.right == null) {

return null;

}

if (node.left == null) {

return node.right;

}

if (node.right == null) {

return node.left;

}

let getSmallest = function(node) {

if(node.left === null && node.right == null) {

return node;

}

if(node.left != null) {

return node.left;

}

if(node.right !== null) {

return getSmallest(node.right);

}

}

let temNode = getSmallest(node.right);

node.data = temNode.data;

node.right = this.removeNode(temNode.right,temNode.data);

return node;

} else if (data < node.data) {

node.left = this.removeNode(node.left,data);

return node;

} else {

node.right = this.removeNode(node.right,data);

return node;

}

}

find(data) {

var current = this.root;

while (current != null) {

if (data == current.data) {

break;

}

if (data < current.data) {

current = current.left;

} else {

current = current.right

}

}

return current.data;

}

}

module.exports = BinarySearchTree;

前言

javascript是一门非常灵活的语言,实际的开发过程中我们也可以灵活的使用它而给我们的工作带来便利,这篇文章记录了自己平时学习过程中经常用到的一些小技巧,整理出来作为笔记,也希望对感兴趣的同学有所帮助。( 持续更新… )

1 获取指定范围内的随机数

当我们需要获取指定范围(min,max)内的整数的时候,下面的代码非常适合。

1

2

3

function getRadomNum(min,max){

return Math.floor(Math.random() * (max - min + 1)) + min;

}

测试

2 随机获取数组中的元素

1

2

3

function getRadomFromArr(arr){

return arr[Math.floor(Math.random()*arr.length)];

}

测试

3 生成从0到指定值的数字数组

1

2

3

var arr=[],length=100,i=1;

for(;arr.push(i++)

console.log(arr)

测试

4 打乱数字数组的顺序

1

2

var arr = [1,2,3,4,5,6,7,'a','dsfs',8,9,'v'];

arr.sort(function(){return Math.random()-0.5});

测试

5 对象转换为数组

1

2

3

4

5

6

7

8

9

10

11

//注意对象必须是以下格式的才可以通过此方式转化为数组

//获取的DOM集合,以及函数的arguments也可以通过此方式转化为数组

var obj={

0:'qian',

1:'long',

2:'chu',

3:'tian',

length:4

}

var _slice=[].slice;

var objArr=_slice.call(obj);

测试

6 验证是否为数组

1

2

3

function isArray(obj){

return Object.prototype.toString.call(obj) === '[object Array]' ;

}

测试

7 获取数组中最大或者最小值

1

2

3

4

5

6

function maxAndMin(arr){

return {

max:Math.max.apply(null,arr.join(',').split(',')),

min:Math.min.apply(null,arr.join(',').split(','))

}

}

该方法适合一维或者多维数组求最大最小值的情况

测试

8 清空数组

1

2

3

4

5

6

7

8

9

10

11

//方式一 通过将长度设置为0

var arr=[1,2,3,4,5];

arr.length=0;

//方式二 通过splice方法

var arr=[1,2,3,4,5];

arr.splice(0,arr.length);

//方式三 通过将空数组 [] 赋值给数组(严格意义来说这只是将ary重新赋值为空数组,之前的数组如果没有引用在指向它将等待垃圾回收。)

var arr=[1,2,3,4,5];

arr=[];

9 保留指定小数位

1

2

var num =4.345678;

num = num.toFixed(4); // 4.3457 第四位小数位以四舍五入计算

10 不要直接使用delete来删除数组中的元素

数组在js中也是对象,有时候我们可能会通过delete来删除数组中的元素,但是其实仅仅是将数组的元素的值赋值为了undefined。

1

2

3

var arr=[1,2,3,4,5,'谦龙','雏田'];

delete arr[5];

console.log(arr,arr[5],arr.length);

测试

可以通过splice来删除数组中的某一项

1

2

3

var arr=[1,2,3,4,5,'谦龙','雏田'];

arr.splice(5,1);

console.log(arr,arr[5],arr.length);

测试

11 生成指定长度的随机字母数字字符串

1

2

3

4

5

function getRandomStr(len) {

var str = "";

for( ; str.length < len; str += Math.random().toString(36).substr(2));

return str.substr(0, len);

}

测试

12 null 与 undefined

null == undefined,null == null 返回true,有时候我们为了排除null 和 undefined可以使用如下的代码

1

2

3

4

5

function test(obj){

if(obj!=null){// obj除了undefined 和 null 之外都会走这里

....这里写代码逻辑

}

}

13 找出数组中出现次数最的元素,并给出其出现过的位置

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

function getMaxAndIndex(arr ){

var obj = {};

arr.forEach(function(item,index){

if(!obj[item]){

obj[item]= {indexs: [index]}

}else{

obj[item]['indexs'].push(index);

}

});

var num=0;//记录出现次数最大值

var str='';//记录出现次数最多的字符

var reArr;//返回最大值的位置数组

for(var attr in obj){

var temp=obj[attr]['indexs'];

if(temp.length>num){

num=temp.length;

str=attr;

reArr=temp;

}

}

return {

maxStr:str,

indexs:reArr

}

}

测试结果

array 前端面试题_前端面试中的常见的算法问题相关推荐

  1. array 前端面试题_web前端开发面试题汇总

    前端面试题汇总 第一部分HTML&CSS 1. 浏览器分类 浏览器:IE,Chrome,FireFox,Safari,Opera. 内核:Trident,Gecko,Presto,Webkit ...

  2. array 前端面试题_一则关于js数组的前端面试题

    假设,有一个数组为[1,2,3,4,5]:再给定一个数字如7,将数组间的值进行加法运算,怎么求出最后结果为[2,5],[3,4],[1,2,4]?const sumArray = arr =>  ...

  3. 【前端面试题】前端基础 | 八股文 | HTTP网络 | Vue | React

    ⭐️ 本文首发自 前端修罗场(点击加入),是一个由 资深开发者 独立运行 的专业技术社区,我专注 Web 技术.Web3.区块链.答疑解惑.面试辅导以及职业发展.博主创作的 <前端面试复习笔记& ...

  4. 前端面试题集锦——前端综合问题

    前端综合问题 前端页面有哪三层构成,分别是什么?作用是什么? 1)结构层(html)structural layer 由HTML或者XHTML之类的标记语言负责创建,即:标签: 2)表示层(css)p ...

  5. 前端面试题(持续更新中)

    全家桶项目源码:Vue全家桶+SSR+Koa2全栈开发美团网[完整版] 链接:https://pan.baidu.com/s/1cwPDVkj_I5z568mYIHni4A 提取码:24g2 2020 ...

  6. 前端面试题大全持续更新中……

    目录 1.nextTick知道嘛,实现原理是什么? 2.检测数据类型的方法 3.vue切换路由不重新渲染_Vue路由切换时页面内容没有重新加载 4.JavaScript开发中的23种设计模式详解 5. ...

  7. java web前端面试题_web前端笔试试题(答案)

    一.填空题(每空1分,共70分) 1.JS中的数据类型有哪些__string,number,undefined,null,boolean,Object Array,Function,:(3分) 2.J ...

  8. 应届生web前端面试题_史上最全前端面试题(含答案)

    2015-10-30 06:30:03 阅读( 385 ) HTML+CSS 1.对WEB标准以及W3C的理解与认识 标签闭合.标签小写.不乱嵌套.提高搜索机器人搜索几率.使用外 链css和js脚本. ...

  9. 前端面试题,前端组件化、工程化、模块化的概念

    1.前端模块化: 可以理解为一组自定义业务的抽象封装,是根据项目的情况来进行封装组合到一起的,比如我们可以分为登录模块,评论模块.模块可维护性好,组合灵活,方便调用,多人协作互不干扰. 2.前端组件化 ...

  10. mysql关于时间的面试题_关于面试中的mysql试题1

    1.按时间列出每天输赢的量 ----> SELECT W_Time,COUNT(CASE WHEN WoR='赢' THEN 1 END) AS 赢, COUNT(CASE WHEN WoR=' ...

最新文章

  1. Corrigendum: A window into third generation sequencing
  2. Exchange服务器系列课程之四--管理Exchange收件人
  3. Qt Creator添加调试器
  4. 利率计算中的套路!用 Python 告诉你究竟亏了多少!
  5. Marketing Cloud launchpad中的meta标签
  6. rasa聊天机器人_Rasa-X是持续改进聊天机器人的独特方法
  7. 关注!部分高校公布暑假时间,暑假将弹性调整?
  8. 集合各实现类的底层实现原理
  9. python下载url链接_使用Python从url地址下载所有pdf文件
  10. 话里话外:企业ERP实施的前前后后(二)
  11. 在vue中使用tinymce富文本编辑器+tinymce富文本编辑器插入图片+自定义菜单按钮封装+vue-tinymce富文本
  12. scipy短时傅里叶分析STFT
  13. Oracle配置本地网络服务器测试不成功,无监听程序
  14. oracle误删数据恢复方法
  15. 下载、预览PDF报错问题排查
  16. java timeunit_java并发之TimeUnit
  17. 写好 JS 条件语句的 5 条守则
  18. 如何利用在线帮助中心解决客户问题?
  19. apt-get: relocation error:/libapt-private.so.0.0 version APTPKG_5.0 not defined in file libapt-pkg
  20. JavaScript——计算平方值

热门文章

  1. 脚踏实地、仰望星空的贵系学子们
  2. 毕业设计之甘特图制作
  3. MySQL专题系统归纳快速上手(常用cmd命令,常用函数汇总,SQL语句精讲带示例)适用初学、用法速查
  4. 手把手教你写 Word 版本PRD
  5. 网站项目计划书模板范本
  6. 什么是 P2P、P2C 、O2O 、B2C、B2B、 C2C
  7. python开发板 树莓派_树莓派3代B+型 Raspberry Pi 3b+电脑linux开发板python编程
  8. win10系统崩溃怎么修复_系统崩溃!win10系统修复和数据恢复方法总结
  9. python中chr()和ord()函数的用法
  10. fgetc getc函数