来源:牛客网
1.函数柯里化
题目链接:https://www.nowcoder.com/practice/bb78d69986794470969674a8b504ac00?tpId=6&tqId=10977&tPage=2&rp=2&ru=/ta/js-assessment&qru=/ta/js-assessment/question-ranking
题目描述
已知 fn 为一个预定义函数,实现函数 curryIt,调用之后满足如下条件:
1、返回一个函数 a,a 的 length 属性值为 1(即显式声明 a 接收一个参数)
2、调用 a 之后,返回一个函数 b, b 的 length 属性值为 1
3、调用 b 之后,返回一个函数 c, c 的 length 属性值为 1
4、调用 c 之后,返回的结果与调用 fn 的返回值一致
5、fn 的参数依次为函数 a, b, c 的调用参数
示例1
输入
var fn = function (a, b, c) {return a + b + c}; curryIt(fn)(1)(2)(3);
输出
6
笔记:
柯里化:把接受多个参数的函数变换成接受一个单一参数(最初函数的第一个参数)的函数,并且返回接受余下的参数而且返回结果的新函数的技术。
题目分析:
将预定义的函数的参数逐一传入到curryIt中,当参数全部传入之后,就执行预定义函数。
- 首先要获得预定义函数的参数个数fn.length。
- 然后声明一个空数组去存放这些参数。
- 返回一个匿名函数接收参数并执行,当参数个数小于fn.length,则再次返回该匿名函数,继续接收参数并执行,直至参数个数等于fn.length。
- 最后,调用apply执行预定义函数。
function curryIt(fn) {
//获取fn参数的数量
var n = fn.length;
//声明一个数组args
var args = [];
//返回一个匿名函数
return function(arg){
//将curryIt后面括号中的参数放入数组
args.push(arg);
//如果args中的参数个数小于fn函数的参数个数,
//则执行arguments.callee(其作用是引用当前正在执行的函数,这里是返回的当前匿名函数)。
//否则,返回fn的调用结果
if(args.length < n){
return arguments.callee;
}else return fn.apply("",args);
}
}
2.剪绳子
题目链接:https://www.nowcoder.com/practice/57d85990ba5b440ab888fc72b0751bf8?tpId=13&&tqId=33257&rp=1&ru=/activity/oj&qru=/ta/coding-interviews/question-ranking
题目描述
给你一根长度为n的绳子,请把绳子剪成整数长的m段(m、n都是整数,n>1并且m>1),每段绳子的长度记为k[0],k[1],…,k[m]。请问k[0]xk[1]x…xk[m]可能的最大乘积是多少?例如,当绳子的长度是8时,我们把它剪成长度分别为2、3、3的三段,此时得到的最大乘积是18。
输入描述:
输入一个数n,意义见题面。(2 <= n <= 60)
输出描述:
输出答案。
示例1
输入
8
输出
18
笔记:
举例子,看规律。
4 : 2x2
5 : 2x3
6 : 3x3
7 : 2x2x3 或者4x3
8 : 2x3x3
9 : 3x3x3
10:2x2x3x3 或者4x3x3
11:2x3x3x3
12:3x3
13:2x2x3x3x3 或者4x3x3x3
- 首先判断k[0]到k[m]实际上只可能是2、3、4(4=2x2)。
- 其次看2和3的数量,2的数量肯定小于3个:2x2x2<3x3。
- 用n除以3,根据得到的余数判断是一个2还是两个2还是没有2。
*两个特殊情况: 由于题目规定m>1,所以2只能是1x1,3只能是2x1。
function cutRope(number)
{
if(number==2){
return 1;
}
if(number==3){
return 2;
}
var x = number % 3;
var y = Math.floor(number / 3);
if(x==0){
return Math.pow(3,y);
}else if(x==1){
return 2*2*Math.pow(3,y-1);
}else{
return 2*Math.pow(3,y);
}
}
3.二维数组
题目链接:https://www.nowcoder.com/practice/abc3fe2ce8e146608e868a70efebf62e?tpId=13&&tqId=11154&rp=1&ru=/activity/oj&qru=/ta/coding-interviews/question-ranking
题目描述
在一个二维数组中(每个一维数组的长度相同),每一行都按照从左到右递增的顺序排序,每一列都按照从上到下递增的顺序排序。请完成一个函数,输入这样的一个二维数组和一个整数,判断数组中是否含有该整数。
分析:
观察数组规律
按照题目要求,数组的特点是:每一行都按照从左到右递增的顺序排序,每一列都按照从上到下递增的顺序排序。
function Find(target, array)
{
const len = array.length;
if(!len){
return false;
}
var len_1 = array[0].length;
if(!len_1){
return false;
}
let row = 0;
let col =len_1-1;
while(row < len && col>=0){
if(array[row][col] === target){
return true;
}
else if(array[row][col] > target){
--col;
}
else{
++row;
}
}
return false;
}
4.跳台阶
题目链接:https://www.nowcoder.com/practice/8c82a5b80378478f9484d87d1c5f12a4?tpId=13&&tqId=11161&rp=1&ru=/activity/oj&qru=/ta/coding-interviews/question-ranking
题目描述
一只青蛙一次可以跳上1级台阶,也可以跳上2级。求该青蛙跳上一个n级的台阶总共有多少种跳法(先后次序不同算不同的结果)。
分析:
找规律
n=1:1种方法;
n=2:2种方法;
n=3:3种方法;
n=4:5种方法;
n=5:8种方法;
n=6:13种方法;
所以,本质上是斐波那契数列:f(n)=f(n-1)+f(n-2)。
function jumpFloor(number)
{
if(number <= 3)
return number;
else{
var f0 = 2;
var f1 = 3;
for(var i=4; i<=number; i++){
f2 = f0 + f1;
f0 = f1;
f1 = f2;
}
return f2;
}
}
5.调整数组顺序
题目链接:https://www.nowcoder.com/practice/beb5aa231adc45b2a5dcc5b62c93f593?tpId=13&&tqId=11166&rp=2&ru=/activity/oj&qru=/ta/coding-interviews/question-ranking
题目描述
输入一个整数数组,实现一个函数来调整该数组中数字的顺序,使得所有的奇数位于数组的前半部分,所有的偶数位于数组的后半部分,并保证奇数和奇数,偶数和偶数之间的相对位置不变。
分析:
- 删除原数组中的偶数。
- 把原数组中的偶数按顺序保存在新的数组中。
- 把只有奇数的数组和只有偶数的数组拼接成新数组。
function reOrderArray(array)
{
//删除数组种的偶数,返回新数组(只包含奇数)
var odd = array.filter(function(value,index,array){
return value % 2 !== 0;
});
var newArray=[];
//把数组中的偶数按顺序添加到index中
for(var i=0; i<array.length; i++){
if(array[i]%2 == 0){
newArray.push(array[i]);
}
}
//奇数数组和偶数数组拼接
var result = odd.concat(newArray);
return result;
}
6.顺时针打印矩阵
题目链接:https://www.nowcoder.com/practice/9b4c81a02cd34f76be2659fa0d54342a?tpId=13&&tqId=11172&rp=3&ru=/activity/oj&qru=/ta/coding-interviews/question-ranking
题目描述
输入一个矩阵,按照从外向里以顺时针的顺序依次打印出每一个数字,例如,如果输入如下4 X 4矩阵: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 则依次打印出数字1,2,3,4,8,12,16,15,14,13,9,5,6,7,11,10.
分析:
顺时针打印就是按照顺时针转圈打印,打印方向:
- 从左到右;
- 从上到下;
- 从右到左;
- 从下到上。
因此,定义四个边界:左、右、上、下。
for循环遍历行走的方向。
根据边界范围判断是否打印完成。
function printMatrix(matrix)
{
var row = matrix.length;
var col = matrix[0].length;
var left = 0;
var right = col-1;
var top = 0;
var bottom = row-1;
var arr = [];
if(row == 0 || col == 0){
return arr;
}
while(left<=right && top<=bottom){
//从左到右
for(var i=left;i<=right;i++)
arr.push(matrix[top][i]);
//从上到下
for(var i=top+1;i<=bottom;i++)
arr.push(matrix[i][right]);
if(top!=bottom){
//从右到左
for(var i=right-1;i>=left;i--)
arr.push(matrix[bottom][i]);
}
if(left!=right){
// 从下到上
for(var i=bottom-1;i>top;i--)
arr.push(matrix[i][left]);
}
left++;
right--;
top++;
bottom--;
}
return arr;
}