Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

daily: elevator dispatch 2019-07-31 #103

Merged
merged 36 commits into from
Aug 20, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
36 commits
Select commit Hold shift + click to select a range
3520b4f
feat: longest harmonious subsequence
EdgeAsh Jul 19, 2019
72a39d1
daily: Longest Harmonious Subsequence, option 1
EdgeAsh Jul 21, 2019
8c7c317
alternative solutions.
EdgeAsh Jul 24, 2019
b45665a
Update 2019-06-20.md
azl397985856 Jul 25, 2019
9739216
feat: date 2019.06.17
EdgeAsh Jul 25, 2019
190d85c
fix: add tag.
EdgeAsh Jul 26, 2019
9e5152a
pref: optimize code.
EdgeAsh Jul 30, 2019
327da5c
feat: 2019-07-31 elevator dispatch
EdgeAsh Aug 12, 2019
9985bca
alternative solutions.
EdgeAsh Jul 24, 2019
cd96db9
Update 2019-06-20.md
azl397985856 Jul 25, 2019
dc08600
Update 2019-06-20.md
azl397985856 Jul 25, 2019
42a4a61
pref: optimize code.
EdgeAsh Jul 30, 2019
c892276
pref: one code for each solution.
EdgeAsh Jul 30, 2019
bfa39fe
feat: longest harmonious subsequence
EdgeAsh Jul 19, 2019
b268974
alternative solutions.
EdgeAsh Jul 24, 2019
fd41f89
Update 2019-06-20.md
azl397985856 Jul 25, 2019
53ec39f
fix: title incorrect.
EdgeAsh Aug 12, 2019
9a4d0fa
alternative solutions.
EdgeAsh Jul 24, 2019
005f92e
Update 2019-06-20.md
azl397985856 Jul 25, 2019
076f58e
feat: longest harmonious subsequence
EdgeAsh Jul 19, 2019
67895ba
daily: Longest Harmonious Subsequence, option 1
EdgeAsh Jul 21, 2019
d3d15da
alternative solutions.
EdgeAsh Jul 24, 2019
04b2fb8
Update 2019-06-20.md
azl397985856 Jul 25, 2019
4ca4be2
feat: date 2019.06.17
EdgeAsh Jul 25, 2019
125e467
fix: add tag.
EdgeAsh Jul 26, 2019
42c7745
pref: optimize code.
EdgeAsh Jul 30, 2019
1a95cd3
alternative solutions.
EdgeAsh Jul 24, 2019
ed06675
Update 2019-06-20.md
azl397985856 Jul 25, 2019
6dbe5b3
Update 2019-06-20.md
azl397985856 Jul 25, 2019
8b6cc94
pref: optimize code.
EdgeAsh Jul 30, 2019
9fb25e9
pref: one code for each solution.
EdgeAsh Jul 30, 2019
2bd3ac8
feat: 2019-07-31 elevator dispatch
EdgeAsh Aug 11, 2019
04470bf
pref: more one good solution.
EdgeAsh Aug 19, 2019
7a4feba
fix: unnecessary change
EdgeAsh Aug 19, 2019
4c82739
Update 136.single-number.md
EdgeAsh Aug 19, 2019
e6caed5
Update 2019-07-31.md
EdgeAsh Aug 19, 2019
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
149 changes: 149 additions & 0 deletions daily/2019-07-31.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,149 @@
## 每日一题 - 小飞电梯调度问题

### 信息卡片

- 时间: 2019-07-31
- 题目链接:暂无
- tag:`Math` `Dynamic Programming`

### 题目描述:

```
微软亚洲研究所所在的希格玛大厦一共有6部电梯。在高峰时间,每层都有人上下,电梯在每层都停。实习生小飞常常会被每层都停的电梯弄得很不耐烦,于是他提出了这样一个办法:
由于楼层并不太高看没在繁忙的上下班时间,每层电梯从一层往上走时,我们只允许电梯停在其中的某一层。所有的乘客都从一楼上电梯,到达某层楼后,电梯停下来,所有乘客再从这里爬楼梯到自己的目的层。
在一楼的时候,每个乘客选择自己的目的层,电梯则自动计算出应停的楼层。
问:电梯停在哪一层楼,能够保证这次乘坐电梯的所有乘客爬楼梯的层数之和最少。

扩展:

1.如何在O(n)的时间复杂度完成?
2.往上爬楼梯,总是比往下走要累的。假设往上爬一个楼层,要耗费k单位的能量,而往下走只需要耗费1单位的能量,那么如果题目条件改为让所有人消耗的能量最少,这个问题怎么解决呢?
这个问题可以用类似上面的分析方法来解答看,因此笔者不再累述,留给读者自行解决。
3.在一个高楼里面,电梯只在某一个楼层停,这个政策还是不太人性化。如果电梯会在k个楼层停呢?读者可以发挥自己的想象力,看看如何寻找最优方案。
```

### 参考答案


题意是
每层都停 => 只停一层,其余让人爬楼梯;所有人爬梯之和最小
选择目的层(i),在i层下的人数是T[i],根据大家选择的目的层计算在哪一层(X)停最优
sum(1~N){T[i]*|i-x|}的最小值

从简单易想到的方式开始;
从1楼开始直到顶层,算出在每层人需要爬梯的总和数组result
找出Min(result)下标
时间复杂度是O(N^2)

```js
/**
* 两个测试数据
* nPerson = [0, 1, 3, 4, 2, 3]
* nPerson = [0, 1, 0, 2, 2, 6]
*/
function original(nPerson) { // nPerson首元素设0,使楼层与下标对应
// nPerson[i] 在i层下的人, N 总楼层
let result = [0]; // 存各层结果
let target = 1; // 最小值下标
for(let x = 1; x < nPerson.length; x++) { // 目标楼层x
result[x]=0;
for(let i = 1; i < nPerson.length; i++) { // 人在哪层停留
result[x] += nPerson[i]*Math.abs(x-i);
}
if(result[target] > result[x]) {
target = x
}
}
return target;
}
```

进一步考虑(动态规划)
假设在i层停,共需要爬Y阶;在i层有N2人,在i层以下共N1人,i层以上共N3人
如果在i-1层停,相比i层变化Y+N2+N3-N1 = Y - (N1-N2-N3) => N1 > (N2 + N3)时会减少爬阶数
如果在i+1层停,相比i层变化Y-N3+N2+N1 = Y - (N3-N2-N1) => N3 > (N2 + N1)时会减少爬阶数
所以在N1 > N2+N3时应该在i-1层停,N3 > N2+N1时应该在i+1层停; 否则在i层停

初始状态电梯停在第一层,向上进行状态的变迁,开始时N2 + N1 - N3 < 0
sum越来越小,直到某一层N2 + N1 >= N3,就没有必要在往上走了。这时已求出最合适的楼层了

```js
function betterOne(nPerson) { // 首元素设空, 下标就与楼层对应了,nPerson的长度-1就是楼层数
let N1 = 0;
let N2 = nPerson[1];
let N3 = 0;
let target = 1;
// 第一层时,算出人需要走的楼梯数Y和在一楼以上的人数N3
for(let i = 2; i < nPerson.length; i++) {
N3 += nPerson[i];
}
// 再来优化
for(let i = 2; i < nPerson.length; i++) {
if (N1+N2 < N3) { // 在i+1层停较优
target = i;
N1 += N2
N3 -= nPerson[i]
N2 = nPerson[i]
} else {
break
}
}
return target
}
```

扩展问题2的解
向上爬比向下走更耗费体力,假设上楼是下楼耗费能量的k倍;k大于1
比较消耗能量的大小决定楼层,只需在动态规划方式上增加权重即可

```js
function betterOnewithWeight(nPerson, k) { // 首元素设空, 下标就与楼层对应了,nPerson的长度-1就是楼层数
let N1 = 0;
let N2 = nPerson[1];
let N3 = 0;
let target = 1;
// 第一层时,算出人需要走的楼梯数Y和在一楼以上的人数N3
for(let i = 2; i < nPerson.length; i++) {
N3 += nPerson[i];
}
// 再来优化
for(let i = 2; i < nPerson.length; i++) {
if (N1+N2 < N3*k) { // 在i+1层停比较好
target = i;
N1 += N2
N3 -= nPerson[i]
N2 = nPerson[i]
} else {
break;
}
}
return target
}
```

### 其他优秀解答
中位数方法

假设两个人在2楼和9楼下。那么在2-9楼之间任意层停,两人走楼梯的层数和是不变的
换一组(第二小、第二大)人也是这么处理
将每个人要去的楼层从低到高逐一排列,找到中位数,此中位数就是最优楼层

时间复杂度O(N)

```js
/**
* 中位数方法
*/
function median(nPerson) {
const newArr = []; // 存楼层
for(let i=0; i < nPerson.length; i++) {
while(nPerson[i] > 0) {
newArr.push(i)
nPerson[i]--
}
}
let len = newArr.length;
// 返回楼层中位数
return len % 2 == 1 ? newArr[(len+1)/2] : newArr[len/2]
}
```
8 changes: 7 additions & 1 deletion daily/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -209,6 +209,12 @@ tag: `几何`

时间:2019-07-30

### [电梯调度问题](./2019-07-31.md)

tag: `Math` `Dynamic Programming`

时间:2019-07-31

### [105.从前序与中序遍历序列构造二叉树](./2019-08-05.md)

tag: `Tree` `Array`
Expand Down Expand Up @@ -241,7 +247,7 @@ tag: `并查集` `BFS`

### [771.jewels-and-stones](./2019-08-22.md)

tag:String` `Hash Table`
tag:`String` `Hash Table`

时间: 2019-08-22

Expand Down