iT邦幫忙

2023 iThome 鐵人賽

DAY 29
0

CodeWars 題目

Link

難度

5 kyu

題目

函數回傳參數陣列中的「峰值」(或局部最大值)的位置和值。
不計算陣列的頭跟尾,並且如過出現峰值連續,只輸出第一個。

思路

峰值表示要陣列元素的前項後項都比自己小。

想像起來,不是需要針對陣列本身做處理;
而是必須要從頭到尾跑過陣列元素,因為峰並不一定只有一個。

因此利用 forEach 迴圈跑陣列元素,利用 index 比對前後項來實作。

實作

function pickPeaks(arr) {
	let result = {
		pos: [],
		peaks: []
	}
	arr.forEach((item, index) => {
		if (arr[index - 1] < item) {
			if (arr[index + 1] < item) {
				result.pos.push(index);
				result.peaks.push(item);
			}
			if (arr[index + 1] === item) {
				const isSmaller = arr.slice(index + 1);
				isSmaller.some(elem => {
					if (elem !== item) {
						if (elem < item) {
							result.pos.push(index);
							result.peaks.push(item);
						}
						return true;
					}
				})
			}
		}
	})
	return result;
}

result 用來儲存紀錄結果。

跑 forEach 迴圈迭代陣列,首先 arr[index - 1] < item 驗證是否大於前項;在這之中繼續判斷,如果又大於後項,毫無懸念直接新增在 result 之中。

但如果等於後項,表示目前與後項相同,有可能是形成一個「平台」;按照題目需求,平台只需要紀錄第一個,但也有可能在連續不知道幾個之後有更大的值,這就並非是「平台」。

因此 slice 擷取在此之後的陣列內容,利用 some 尋找第一個不等於的值。

只要在找到第一個不符合就中斷尋找,並且不能影響到外層的 forEach;找到之後再更進一步判斷是否小於平台值,如果符合就新增在 result 之中。


上一篇
Most frequently used words in a text
下一篇
完賽
系列文
解三十天的 CodeWars30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言