首页 > 试题广场 >

跳柱子

[编程题]跳柱子
  • 热度指数:2965 时间限制:C/C++ 2秒,其他语言4秒 空间限制:C/C++ 256M,其他语言512M
  • 算法知识视频讲解
小易有根柱子,第根柱子的高度为。一开始小易站在第一根柱子上。小易能从第根柱子跳到第根柱子,当且仅当。其中为指定的一个数字。
另外小易拥有一次释放超能力的机会。这个超能力能让小易从柱子跳到任意满足的柱子而无视柱子高度的限制。
现在小易想知道,小易是否能到达第根柱子。

输入描述:
第一行数据组数
对于每组数据,第一行数字,接下来一行个数字表示.



输出描述:
对于每组数据,输出YES或NO
示例1

输入

1
5 3
6 2 4 3 8

输出

YES
示例2

输入

1
5 2
1 8 2 3 4

输出

NO
t = int(input())
for _ in range(t):
    n, k = list(map(int, input().split()))
    li = list(map(int, input().split()))
    dp = [[False, 1] for _ in range(n)]
    dp[0][0] = True
    for i in range(1, n):
        flag = False
        max1 = 0
        for j in range(max(0, i - k), i):
            if dp[j][0] == False:
                continue
            elif li[j] >= li[i]:
                dp[i] = dp[j].copy()
                max1 = max(max1, dp[j][1])
                dp[i][1] = max1
                flag = True
            elif li[j] < li[i] and not flag and dp[j][1]:
                dp[i] = dp[j].copy()
                dp[i][1] = 0
    if dp[-1][0]:
        print('YES')
    else:
        print('NO')

发表于 2020-04-04 13:20:19 回复(7)
#include <cstdio>
#include <cstring>
#include <algorithm>

#define MAX_N 1000+100
int T;
int N, k;
int H[MAX_N];
int dp[MAX_N][3];


int main()
{

	scanf("%d", &T);
	while (T--)
	{
		memset(dp, 0, sizeof(dp));
		dp[0][1] = 1;
		dp[0][0] = 1;
		scanf("%d%d", &N, &k);
		for (int i = 0; i < N; i++)
		{
			scanf("%d", &H[i]);
		}

		for (int i = 1; i < N; i++)
		{
			for (int j = 1; j <= k; j++)
			{
				if (i - j >= 0 && H[i] <= H[i-j]) {
					dp[i][0] |= dp[i - j][0];
					dp[i][1] |= dp[i - j][1];
				}

				dp[i][1] |= dp[i - j][0];
				
				
			}
		}

		if (dp[N - 1][0] || dp[N - 1][1])
			printf("YES\n");
		else
			printf("NO\n");
	}


	return 0;
}

发表于 2020-01-08 20:18:45 回复(0)
#include <iostream>
#include <vector>
using namespace std;

int main() {
	int T = 0;
	cin >> T;  //数据组数
	for (int i = 0; i < T; i++) {
		int n = 0, k = 0;
		cin >> n >> k;
		vector<int> heights(n, 0);
		for (int i = 0; i < n; i++) {
			cin >> heights[i];
		}
		vector<vector<bool>> dp(n, vector<bool>(2, false));
		dp[0][0] = true;  //第一个位置可以到达
		dp[0][1] = false;  //刚开始没有用超能力

		for (int j = 1; j < n; j++) {
			for (int i = 0; i < j; i++) {
				if (j - i > k) continue;  //不满足范围条件
				if (!dp[i][0]) continue;  //如果i不可达
				if (heights[i] >= heights[j] && dp[i][1] == false) {
					//最好情况,之前没有用过超能力,现在也不用
					dp[j][0] = true;
					dp[j][1] = false;
					break;  //避免最好情况被其他情况覆盖
				}
				else if (heights[i] >= heights[j] && dp[i][1] == true) {
					//之前用过超能力,现在不用
					dp[j][0] = true;
					dp[j][1] = true;   //之前用过了
				}
				else if (heights[i] < heights[j] && dp[i][1] == false) {
					//之前没有用过超能力,现在要用
					dp[j][0] = true;
					dp[j][1] = true;
				}
				else if (heights[i] < heights[j] && dp[i][1] == true) {
					//之前用过超能力,现在还要用,说明无法从该i到j,默认false
                    //直接改false会覆盖掉其他情况
					continue;
				}
			}
		}
		if (dp[n - 1][0] == true)
			cout << "YES" << endl;
		else 
			cout << "NO" << endl;
	}
}

发表于 2020-07-20 11:57:27 回复(0)
import java.util.Scanner;

public class Main{
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);
        int T = sc.nextInt();
        int n = 0, k = 0;
        for (int i = 0; i < T; i++) {
            n = sc.nextInt();
            k = sc.nextInt();
            int[] nums = new int[n];
            for (int j = 0; j < n; j++)
                nums[j] = sc.nextInt();
            System.out.println(solution(n, k, nums));
        }
    }

    public static String solution(int n, int k, int[] nums) {
        int big = 1;
        int index = 0;
        while (index < nums.length - 1) {
            int tmp = index;
            int max = 0, max_index = index;
            for (int j = index + 1; j < index + 1 + k && j < nums.length; j++) {
                if (nums[j] < nums[index]) {
                    max_index = (max > nums[j]) ? max_index : j;
                    max = Math.max(nums[j], max);
                }
            }
            index = max_index;
            if (tmp == index && big > 0) {
                big--;
                max = 0;
                max_index = index;
                for (int j = index + 1; j < index + 1 + k && j < nums.length; j++) {
                    max_index = (max > nums[j])? max_index : j;
                    max = Math.max(nums[j], max);
                }
                index = max_index;
            }
            else if (tmp == index && big <= 0)
                return "NO";
        }
        return "YES";
    }
}


编辑于 2020-04-05 19:10:36 回复(0)
var num=parseInt(readline());//数据组数
            while(num>0){
                num--;//减小组数
                //每组有两行
                var r_one=readline();//第一行
                var r_two=readline();//第二行
                var n=parseInt(r_one.split(" ")[0]);//柱子数
                var k=parseInt(r_one.split(" ")[1]);//可跨越的柱子间隔数
                var h_arr=r_two.split(" ");//柱子的高度数组
                h_arr.forEach((item,i)=>{
                    h_arr[i]=parseInt(item)
                })
                var end=h_arr.length-1;//目的柱子的索引
                //console.log(h_arr)
                // //跨越柱子的条件是1<=柱子间隔<=3,并且当前所处柱子高度>目的柱子高度
                // //那么可以遍历柱子间隔,如果在间隔范围内有高度小于等于当前柱子的目的柱子,那么就尝试跳一下
                var start=0;//当前所处柱子
                var j=k;//间隔
                var max_h={height:0,index:0};//最大高度
                var flag=false;//超能力记录
                while(start<end){
                    //中转柱子小于等于的话就可以跳,中转索引是start+j
                    //但是可能在柱子间隔中存在多个可以跳的选项,此时应该选择能跳的最高的柱子!
                    for(var j=1;j<=k;j++){
                        if((start+j)<=end && h_arr[start+j]<=h_arr[start] && h_arr[start+j]>max_h.height){
                            max_h.index=j;//获取可以跳的最高柱子的索引
                            max_h.height=h_arr[start+j];
                            //console.log(max_h.index)
                        }
                    }
                    
                    // 不到万不得已(此时就设置是一步都过不去的时候,那么就使用超能力)
                    if(max_h.index==0){
                        //第一次使用超能路
                        if(!flag){
                            flag=true;//改变标记
                            var h_h_max=0;
                            var max_i=0;
                            for(var j=1;j<=k;j++){
                                if((start+j)<=end && h_arr[start+j]>h_h_max){
                                    h_h_max=h_arr[start+j];
                                    max_i=j;
                                }
                            }
                            start=start+max_i;//跳到最高峰
                        }else{
                            //使用过超能力还是需要再使用一次,那么就置为-1表示失败
                            start=-1;
                            end=-1;
                        }
                    }else{
                        start=start+max_h.index;//跳到别的柱子上
                        max_h.index=0;//恢复初始值
                        max_h.height=0;
                    }
                }
                //console.log(start)
                // //跳到目的柱子上
                if(start==end && start!=-1){
                    print("YES")
                }else{
                    print("NO")
                }
            }
发表于 2019-12-22 23:30:46 回复(0)
直接贪心即可,这题很巧妙:每次跳都选最远且最高的,然后超能力留到跳不动的时候才用。这样O(n)就能解决
发表于 2022-08-22 18:08:46 回复(0)
每次都挑选范围内小于等于本身的最大值,如果不存在就是用魔法挑选范围内的最大值
import java.util.*;
public class Main {
    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);
        int T = in.nextInt();
        List nums;
        while (T-- > 0){
            nums = new ArrayList();
            int n = in.nextInt();
            int k = in.nextInt();
            for (int i = 0; i < n; i++){
                nums.add(in.nextInt());
            }
            boolean ans = crossEnd(nums, k);
            System.out.println((ans == false)?"NO":"YES");
        }
    }
    public static boolean crossEnd(List<Integer> nums,int k){
        int change = 1;
        int index = 0;
        while (index != nums.size() - 1){
            int max = 0,maxIndex = -1;
            int sMax = 0,sMaxIndex = -1;
            int endIndex = Math.min(nums.size(),index + k + 1);
            List<Integer> temp = nums.subList(index + 1,endIndex);
            for (int i = 0; i < temp.size(); i++){
                if (temp.get(i) > sMax && temp.get(i) <= nums.get(index)){
                    sMax = temp.get(i);
                    sMaxIndex = index + i + 1;
                }
                if (temp.get(i) > max){
                    max = temp.get(i);
                    maxIndex = index + i + 1;
                }
            }
            if (sMaxIndex == -1 && change == 1){
                index = maxIndex;
                change--;
            }else if (sMaxIndex == -1 && change == 0)
                return false;
            else {
                index = sMaxIndex;
            }
        }
        return true;
    }
}


发表于 2020-08-19 16:58:26 回复(0)
第一次用贪心算法,想法是每次都往前面找一个hj 比 hi 小的,并且是最远的,如果找不到hj比hi小的,就动用超能力,找一个前面k个中hi最大的。但是结果错了。
于是感觉可能这个题不能用贪心的思路,用回溯的算法实现了,但是回溯的时间复杂度太高了,只通过了30%的case。代码如下:
function canArive2 (hs, k, n) {
    let res = 'NO'
    const rec = (i, canFly) => {
      if (i === n - 1) {
        res = 'YES'
        return
      }
      for (let j = i + 1; j <= i + k && j <= n - 1; j++) {
        if (hs[j] < hs[i] || canFly) {
          let tmpCanFly = canFly
          if (hs[j] > hs[i]) tmpCanFly = false
          rec(j, tmpCanFly)
        }
      }
    }
    rec(0, true)
    return res
}
后面想了一下,感觉应该是可以用贪心的,仔细看了一下我设的条件,“每次都找hj比hi小的,并且最远的”。这里就不对了,题目只是问能不能到达,而不是就一个最短的路径,所以干嘛用最远的呢,想了下,应该是前面k个柱子中比当前柱子低的,其中最高的那个,因为只有找相对高的,后面才可能跳得下去。改变条件后的贪心算法代码如下:
function canArive1 (hs, k, n) {
  let canFly = true
  let i = 0
  while (i < n - 1) {
      // 找i+1 ~ i+k 最远的,而且低的
      let nextIndex = null
      let highestIndex = i + 1
      for (let j = i + 1; j <= i + k; j++) {
        if (hs[j] < hs[i]) nextIndex = j
        if (hs[j] > hs[highestIndex]) highestIndex = j
      }
      if (!nextIndex) {
        if (canFly) {
          nextIndex = highestIndex
          canFly = false
        } else {
          return 'NO'
        }
      }
      i = nextIndex
  }
  return 'YES'
}
测试:
let res = canArive([6,2,4,3,8], 3, 5)
console.log(res) //YES




发表于 2020-08-04 11:32:26 回复(3)
贪心算法+单调队列 , O(n)时间复杂度
#include<iostream>
#include<vector>
#include<deque>
using namespace std;
 
int forword(vector<int>& h, int k, int start){
    int n = h.size();
    deque<pair<int, int>> Q;//单调递减队列
    Q.push_back(make_pair(start, h[start]));
    pair<int, int> cur=Q.front();
    int i=start+1;
    for (; i<n; ++i){
        cur = Q.front();
        if (i-cur.first>k)//超出范围
            Q.pop_front();
        if (Q.empty()) break;
        if (Q.front().second < h[i])
            continue;
        else{
            while(!Q.empty() && Q.back().second<=h[i])
                Q.pop_back();
            Q.push_back({i, h[i]});
        }
    }
    if (!Q.empty())
        return Q.back().first;
    return cur.first;
}

bool solver(vector<int>& h, int k){
    int n = h.size();
    //不使用超能力
    int farest = forword(h, k, 0);
    if (farest+k>=n-1) return true;
    int max_pos=farest;
    //使用超能力跳到后面k个柱子上的最高处
    for (int i=1; i<=k; ++i){
        if (h[farest+i]>=h[max_pos])
            max_pos = farest+i;
    }
    //不使用超能力
    farest = forword(h, k, max_pos);
    return farest==n-1;
}
 
int main(){
    int T;
    cin >> T;
    while (T--){
        int n, k;
        cin >> n >> k;
        vector<int> h(n);
        for (int i=0; i<n; ++i) cin >> h[i];
        if (solver(h, k))
            cout << "YES" << endl;
        else
            cout << "NO" << endl;
    }
    return 0;
}
发表于 2020-07-28 21:33:05 回复(0)
#include<iostream>
(720)#include<vector>
#include <algorithm>
using namespace std;
typedef long long ll;
int main() {
    int t;
    cin >> t;
    while (t--) {
        ll n, k;
        cin >> n >> k;
        vector<ll> h(n);
        for (ll i = 0; i < n; i++) {
            cin >> h[i];
        }
        vector<vector<int>> dp(n, vector<int>(n));
        vector<vector<int>> can_super(n, vector<int>(n));
        dp[0][0] = 1;
        int can_arrive = 0;
        can_super[0][0] = 1;
        for (ll i = 0; i < n; i++) {
            for (ll j = i; j <= min(i + k, n - 1); j++) {
                if (i == j && i != 0) {
                    for (int k = 0; k < i; k++) {
                        dp[i][j] = dp[i][j] | dp[k][j];
                        can_super[i][j] = can_super[i][j] | can_super[k][j];
                    }
                }
                if (h[j] > h[i] && can_super[i][i] == 1) {
                    dp[i][j] = 1;
                    can_super[i][j] = 0;
                }
                else if (h[j] <= h[i] && j!=i && dp[i][i] == 1) {
                    dp[i][j] = 1;
                    can_super[i][j] = can_super[i][i];
                }
            }
            can_arrive += dp[i][n - 1];
           /* if (can_arrive) {
                break;
            }*/
        }
        if (can_arrive) {
            cout << "YES" << endl;
        }
        else {
            cout << "NO" << endl;
        }
 
    }
}

发表于 2020-03-29 11:44:58 回复(2)
动态规划
发表于 2020-09-11 17:23:06 回复(0)
#include<iostream>
#include<algorithm>
#include<cmath>
#include<cstring>
#include<cstdio>
using namespace std;
int t;
int h[1002];
int n,k,temp=0;
int dp[1002];
int pd[1002];
int main(){
    cin>>t;
    while(t!=0){
        t--;
        cin>>n>>k;
        for(int i=1;i<=n;i++){
            cin>>h[i];
        }
        dp[1]=1;
        for(int i=2;i<=n;i++){
            for(int j=1;j<i;j++){
                if(i-j<=k && dp[j]==1 && h[j]>=h[i]){
                    dp[i]=1;
                }
            }
        }
        if(dp[n]==1){
            cout<<"YES"<<endl;
            temp=1;
        }
        if(temp==0){
            for(int i=n-1;i>=1;i--){
                if(n-i<=k && dp[i]==1){
                    dp[n]=1;
                    break;
                }
            }
            if(dp[n]==1) {
                cout<<"YES"<<endl;
                temp=1;
            }
        }
        if(temp==0){
            pd[n]=1;
            for(int i=n-1;i>=1;i--){
                for(int j=n;j>i;j--){
                    if(pd[j]==1 && h[j]<=h[i] && j-i<=k){
                        pd[i]=1;
                    }
                }
            }
            for(int i=1;i<=n;i++){
                for(int j=n-1;j>=1;j--){
                    if(dp[i]==1 && pd[j]==1 && j-i<=k){
                        i=n+1;
                        j=0;
                        cout<<"YES"<<endl;
                        temp=1;
                    }
                }
            }
        }
        if(temp==0) cout<<"NO"<<endl;
        memset(h,0,sizeof(h));
        memset(dp,0,sizeof(dp));
        memset(pd,0,sizeof(pd));
        temp=0;
    }
//return 0;
}

发表于 2020-08-12 21:42:30 回复(0)
import java.util.*;

public class Main{
    public static boolean solution(int[] nums, int k){
        int n = nums.length;
        boolean[][] dp = new boolean[n][2]; 
        dp[0][0] = true;
        dp[0][1] = true;
        for (int i = 1; i < n; i++){
            for (int j = 1; j <= k && i - j >= 0; j++){
                if (nums[i-j] >= nums[i]){
                    dp[i][0] |= dp[i-j][0]; 
                    dp[i][1] |= dp[i-j][1];
                }
                dp[i][1] |= dp[i-j][0]; 
            }
        }
        return dp[n-1][0] || dp[n-1][1];
    }
    public static void main(String[] args){
        Scanner input = new Scanner(System.in);
        int T = input.nextInt();
        for (int i = 0; i < T; i++){
            int n = input.nextInt();
            int k = input.nextInt();
            int[] nums = new int[n];
            for (int j = 0; j < n; j++){
                nums[j] = input.nextInt();
            }
            if(solution(nums,k)){
                System.out.println("YES");
            }else{
                System.out.println("NO");
            }
        }
    }
}

发表于 2020-08-08 11:08:06 回复(0)
function test (n, k, arrc) {
  let map = new Map(), arr = [0].concat(arrc)
  map[1] = true
  let flag = 0, last = -1
  for (let i = 2; i <= n; ++i) {
      for (let j = i - 1; j >= i - k && j >= 1; --j) {
          if (map[j] && arr[j] >= arr[i]) {
              map[i] = true
              if (i + k >= n) {
                  return true
              }
              flag = 0
              last = -1
              break
          } 
      }
      if (!map[i]) {
          if (!flag) {
              last = i
          }
          flag++
          if (flag === k) {
              break
          }
      }
  }
  if (last !== -1) {
      let max = arr[last], index = -1
      for (let i = last; i <= n && i <= last + k - 1; ++i) {
          if (max <= arr[i]) {
              max = arr[i]
              index = i
          }
      }
      if (index !== -1) {
          map[index] = true
          for (let i = index + 1; i <= n; ++i) {
              for (let j = i - 1; j >= i - k && j >= 1; --j) { 
                  if (map[j] && arr[j] >= arr[i]) {
                      map[i] = true
                      break
                  }
              }
          }
      }
  }
  return !!map[n]
}

var readline = require('readline');

var rl = readline.createInterface({
    input:process.stdin,
    output:process.stdout
});

let inputs = [], pr = 0
rl.on("line", line => {
  inputs.push(line.trim())
  let n = +inputs[0]
  if (inputs.length === (n*2+1)) {
    for(var h = 0; h < n; h++){
      var nu = inputs[h*2+1].split(' ').map(Number)[0]
      var k = inputs[h*2+1].split(' ').map(Number)[1]
      var arr = inputs[h*2+2].split(' ').map(Number)
      console.log(test(nu, k, arr) ? 'YES' : 'NO')
    }
  }
});

/*
  1
  10 5
  5 2 10 7 6 9 4 1 3 8
  No
  1
  10 4
  1 3 4 2 7 5 6 8 10 9
  1
  10 2 
  8 2 7 5 3 9 1 4 6 10
*/ 

发表于 2020-08-08 08:38:11 回复(0)
<p>判断能否到达i,则遍历i-k~i-1的所有柱子,看从这个柱子能否到达i,并要最大程度保留超能力,即只要i-k~i-1有一个可以到达i且保留住超能力的,则到达i就还有超能力。</p><p>超能力在i没有办法向前进一个的时候使用,从i可以到达的柱子也很明确,i+1~i+k都可以到达,且到达的时候都没有超能力了,然后再继续从i+1~i+k往前走,看能否走到最后一个柱子,只要有一个可以走到就是可达。</p><p><br></p>
发表于 2020-08-07 23:43:06 回复(0)
t = int(input())   #case0%,哪位精通python的大神可以给我这个小白指点一下为什么错了
res = []
k = []
for i in range(t):
    l = list(map(int, input().split(' ')))
    k.append(l[1])
    res.append(list(map(int, input().split(' '))))

def fly(li, s):
    pos = 0
    a = 1
    while pos < len(li) - 1:
        if li[pos] >= li[pos + 1]:
            pos = pos + 1
        elif a == 1:
            pos = pos + s
            a = 0
        else:
            print('NO')
            break
    if pos >= len(li) - 1:
        print('YES')

for i in range(t):
    fly(res[i], k[i])
发表于 2020-08-07 23:20:05 回复(0)
public class Main_3 {
    public static void main(String[] args) {
        Scanner input = new Scanner(System.in);
        int T = input.nextInt();
        for (int i = 0; i < T; i++)  {
            int n = input.nextInt();
            int k = input.nextInt();
            int[] nums = new int[n];
            // 完成nums的赋值,得到nums数组
            for (int j = 0; j < n; j++) {
                nums[j] = input.nextInt();
            }
            // print output
            if (JumpPillar(n,k,nums)){
                System.out.println("YES");
            } else {
                System.out.println("NO");
            }
        }
    }

    public static boolean JumpPillar(int n, int k, int[] nums) {
        // nums数组表示的是每个柱子的高度 柱子数为n 最大跳跃距离为k 超能跳跃只能使用1次
        // 由题知,柱子有n个,跳跃方式有2个,可由此确定状态
        // 状态 f[n][2]:能否通过正常跳跃或者超能跳跃到达n
        // f[n][0]:正常跳跃,f[n][1]:超能跳跃
        boolean[][] dp = new boolean[n][2];

        // initialization:在第一个柱子上不用跳直接可以到达
        dp[0][0] = dp[0][1] = true;

        /*
        最后可以到达柱子n ==> 最后一跳只有两种可能,普通跳跃和超能跳跃
        假设前面起跳位置为i,且最后一跳为超能跳跃,那么从第一个到第i个肯定全部是普通跳跃
        假设前面起跳位置为i,且最后一跳为普通跳跃,那么前面就存在一个超能跳跃的可能
        子问题:所以推广到任意一个j到i的位置,j可以使用两种到i的方式:普通或者超能
        Note:如果j采用普通到达的,那么后续它可以使用超能,但是如果j是采用超能到达的,后续就不能使用超能了
         */

        // from j to i
        for (int i = 0; i < n; i++) {
            // 对任意一个目标位置i,j的取值范围只能在[i-k, i-1]
            for (int j = i-1; j>=0 && j >= i-k; j--) {
                // j采用的是普通跳跃
                if (dp[j][0]) {
                    // from j to i:满足高度可以普通到达,不满足可以超能跳跃
                    if (nums[j] >= nums[i]) {
                        dp[i][0] = true;    // 普通
                    } else {
                        dp[i][1] = true;    // 超能
                    }
                }
                // j采用超能跳跃
                if (dp[j][1]) {
                    if (nums[j] >= nums[i]) {
                        dp[i][1] = true;
                    }
                }
            }
        }

        return dp[n-1][1];
    }
}

发表于 2020-08-07 10:14:11 回复(0)
import java.util.*;

public class Main {
    public static void main(String [] args) {
                // 从前往后走,第一个柱子开始,统计后面k个柱子的最高柱子和小于等于当前柱子的最高柱子的坐标。
                // 在代码中分别为 m_i, 和 n_i
                // 如果没有小于等于当前柱子的,也就是没法走,尝试使用超能力,不能用了,就NO,能用就走到m_i
                // 如果有小于等于当前柱子的,走到 n_i
                // 总的来说是贪心的想法,如果能走,走能走的柱子中最高的;不能走,走包括不能走的最高的      
                Scanner sc = new Scanner(System.in);
        int t = sc.nextInt();
        for (int a = 0; a<t; a++) {
            int n = sc.nextInt(),k = sc.nextInt();
            int [] num = new int[n];
            for (int i=0; i<n; i++) num[i] = sc.nextInt();
            int cnt = 0,flag = 1;
            for (int i=0; i<n; ) {
                if (i == n-1) {
                    System.out.println("YES");
                    break;
                }
                int max = 0,nextMax = 0,m_i = -1,n_i = -1;
                for (int j=i+1; j<=i+k&&j<n ; j++) {
                    if (num[j]<=num[i] && num[j]>nextMax) {
                        nextMax = num[j];
                        n_i = j;
                    }
                    if (num[j]>max) {
                        max = num[j];
                        m_i = j;
                    }
                }
                if (nextMax == 0) {
                    if (flag == 1) {
                        flag = 0;
                        i = m_i;
                    }
                    else {
                        System.out.println("NO");
                        break;
                    }
                }
                else {
                    i = n_i;
                }
            }
        }
    }
}

发表于 2020-08-06 14:35:57 回复(0)
是我理解错题意了吗?
10 3 32527223 379970401 613897794 23852042 908033365 15395641 107004106 496628115 152860947 11966641
这个数据为什么可以跳到最终点?一开始就要使用超能力,后面又有一个9亿多的柱子。
为什么呢???
发表于 2020-08-05 12:50:48 回复(1)
var num = readline()
for (var i = 1; i <= num; i++) {
    var line = readline();
    var line1 = readline();
    var arr1 = line.split(' ')
    var arr = line1.split(' ')
    var n = arr1[0]; var k = arr1[1]
    var count = 1;
    function sortNum(a,b){
        if (a-b>0)
        return 1;
        else return 0
    };
    while (arr.length > 1) { 
        var max = 0;
        var max1 = 0;
        for (var j = 1; j <= (k < arr.length - 1 ? k : arr.length - 1); j++) {
            if (sortNum(arr[0],arr[j]) && sortNum(arr[j],max)) {
                var maxindex = j
                max = arr[j]
            }
            if (sortNum(arr[j],max1)) {
                var max1index = j
                max1 = arr[j]
            }
        }
        if (max==0) {
            if (count == 0) {
                console.log('NO')
                break;
            } else {
                arr = arr.slice(max1index)
                count--;
            }
        } else if (max!=0) {
            arr = arr.slice(maxindex)
        }
    }
    if (arr.length <= 1) {
        console.log('YES')
    }
}

发表于 2020-07-15 16:37:23 回复(0)