求多叉树的最大深度
let tree = [
{
id: 1,
children: [
{
id: 2,
children: [
{
id: 3,
children: [
{
id: 4,
}
]
}
]
},
{
id: 5
}
]
},
{
id:6
},
{
id: 7
}
]
console.log(getNodeMaxDepth(tree, 1)) // 3
console.log(getNodeMaxDepth(tree, 2)) // 2
console.log(getNodeMaxDepth(tree, 5)) // 0
console.log(getNodeMaxDepth(tree, 6)) // 0
let const = new Map()
const getNodeMaxDepth = (tree, id) => {
const getTreeMap = tree => {
for (const node of tree) {
map.set(node.id, node)
node.children && getTreeMap(node.children)
}
}
if (map.size === 0) {
getTreeMap(tree)
}
const getMaxDepth = node => {
if (!node || !node.children) return 0
let max = 0
for (const cnode of node.children) {
max = Math.max(max, getMaxDepth(cnode))
}
return max + 1
}
return getMaxDepth(map.get(id))
}
1.对象转换
var entry = {
'a.b.c.dd': 'abcdd',
'a.d.xx': 'adxx',
'a.e': 'ae'
}
// 要求转换成如下对象
var output = {
a: {
b: {
c: {
dd: 'abcdd'
}
},
d: {
xx: 'adxx'
},
e: 'ae'
}
}
function transform(entry) {
var ret = {};
Object.keys(entry).forEach(key => {
const keys = key.split('.');
keys.reduce((prev, curr, i) => {
prev[curr] = i === keys.length - 1 ? entry[key] : (prev[curr] || {});
return prev[curr];
}, ret);
});
return ret;
}
// 从output转为entry
function convert(o) {
var ret = {};
(function inner(o, chain = '') {
for (const key in o) {
if (o.hasOwnProperty(key)) {
var temp = chain;
chain += `${key}.`;
const element = o[key];
if (Object.prototype.toString.call(element) !== '[object Object]' || !Object.keys(element).length) {
ret[chain.substr(0, chain.length - 1)] = element;
} else {
inner(element, chain);
// 返回父节点的链
chain = temp;
}
}
}
})(o)
return ret;
}
2.大数相加
两个字符串整数
var a = '100000012314140000000000000003'
var b = '456789345678945678945678';
function add(a, b) {
let l1 = [...a];
let l2 = [...b];
let max = Math.max(l1.length, l2.length);
while (l2.length !== max) {
l2.unshift(0);
}
while (l1.length !== max) {
l1.unshift(0);
}
l1.reverse();
l2.reverse();
let m = 0;
const ret = l1.reduce((sum, c, i) => {
let t = c + l2[i] + m;
if (t >= 10) {
m = 1;
t -= 10
} else {
m = 0;
}
if (m > 0 && i === l1.length - 1) {
return [...sum, t, m]
}
return [...sum, t,]
}, [])
return ret;
};
}
3.实现 Promise.retry,成功后 resolve 结果,失败后重试,尝试超过一定次数才真正的 reject
Promise.retry = async (promFn, max = 3) =>{
const taskpool = [];
while(max--) {
taskpool.push(promFn);
}
const next = async () => {
try {
let task = taskpool.pop();
console.log('剩余次数', taskpool.length)
const ret = task && await task();
taskpool.length = 0;
return ret;
} catch (error) {
next();
}
}
return next();
}
function promiseGenerator() {
const n = Math.random();
return new Promise((resolve, reject) => {
console.log(n)
setTimeout(() => n > 0.8 ? resolve(n) : reject(n));
}, 1000);
}
Promise.retry(promiseGenerator);
4.不用加减乘除运算符,求整数的7倍
var n = 10
Array.from({length: 7}).fill(n).reduce((a, b) => a + b, 0)
5.求两数之和
给定一个整数数组和一个目标值,找出数组中和为目标值的两个数。
你可以假设每个输入只对应一种答案,且同样的元素不能被重复利用。
示例:
给定 nums = [2, 7, 11, 15], target = 9
因为 nums[0] + nums[1] = 2 + 7 = 9
所以返回 [0, 1]
function calc(arr, target) {
var n = 0;
var map = new Map();
map.set(arr[0], n);
while(n++ <= arr.length) {
var rest = target - arr[n];
if (map.has(rest)) {
return [map.get(rest), n]
} else {
map.set(rest, n);
}
}
}
6.数组分类
var arr = [1,2,3,5,6, 8, 9, 10, 13, 15, 17];
转换成=> [[1,2,3], [5, 6], [8,9,10], [13], [15], [17]]; 递增为1的放在一起
function sort(randomArr) {
return [...new Set(randomArr.sort((a, b) => a - b))].reduce((prev, curr) => {
var last = prev[prev.length -1];
if (Array.isArray(last)) {
var lastele = last[last.length -1];
if (lastele - curr === -1) {
prev.pop();
return [...prev, [...last, curr]]
}
}
return [...prev, [curr]]
}, []);
}
LazyMan
Scheduler
class Scheduler {
taskpool = [];
limit = 2;
add(promise) {
return new Promise((resolve) => {
this.taskpool.push(async() => {
await promise();
resolve();
})
})
}
start() {
while(this.limit--) {
this.next();
}
}
async next() {
if(this.taskpool.length) {
await this.taskpool.shift()();
this.next();
}
}
}
const timeout = time => new Promise(rs => setTimeout(rs, time))
const scheduler = new Scheduler();
const addTask = async (time, order)=> {
await scheduler.add(() => timeout(time));
console.log(order);
}
addTask(1000, 1);
addTask(2000, 2);
addTask(1000, 3);
addTask(1000, 4);
// 1s后输出1
// 2s后输出2, 3
// 3s后输出4
scheduler.start();
scheduler失败重试
<script>
class Scheduler {
constructor(max = 6) {
this.max = max;
this.taskPool = [];
}
pushTask(promiseFn) {
return new Promise((resolve, reject) => {
this.taskPool.push({
request: promiseFn,
exector: { resolve, reject },
});
});
}
async next() {
if (!this.taskPool.length) return;
const task = this.taskPool.shift();
const { request, exector } = task;
try {
const res = await request();
exector.resolve(res);
this.next();
} catch (error) {
exector.reject(error);
this.next();
}
}
run() {
let max = this.max;
while (max-- > 0) {
this.next();
}
}
}
// 假装是一个耗时请求
const req = () => {
return new Promise((rs, rj) => {
setTimeout(() => {
const n = Math.random() * 100;
if (n > 20) {
rs(n);
} else {
rj(n);
}
}, 500);
});
};
var scheduler = new Scheduler();
// 假装并发
for (let i = 0; i < 20; i++) {
scheduler.pushTask(req).then(console.log);
}
scheduler.run();
setTimeout(() => {
scheduler.pushTask(req).then(console.log);
scheduler.run();
}, 3000);
</script>