#2 DeBug日志

YBT P1243 GeBug日志

题目

【题目描述】

输入n个数,从小到大将它们输出,重复的数只输出一次。保证不同的数不超过500个。

【输入】

第一行是一个整数n。1≤n≤100000。

之后n行,每行一个整数。整数大小在int范围内。

【输出】

一行,从小到大不重复地输出这些数,相邻两个数之间用单个空格隔开。

【样例】

7 5
100
400
300
100
500
101
400
500

代码

int a[100099],m,n;
bool cmp(int x){
    int ans = 1;
    int tot = x;
    for(int i = 1;i <= n; i++){
        // cout << a[i] << ':' << tot << ':' << ans << endl ;
        if(a[i] > x) return true;
        if(tot >= a[i]){
            tot -= a[i];
        }
        if(tot < a[i+1]){
            tot = x;
            ans++;
        }
    }
    // cout << ans << endl;
    return ans > m; ①
}
int main(){
    cin >> n >> m;
    int sum = 0;
    int l = 0,r = sum,mid;
    for(int i = 1;i <= n; i++){
        cin >> a[i];
        sum += a[i]; ②
        l = max(a[i],l);
    }
    r = sum;
    int ans;
    while(r >= l){ ③
        mid = (l + r) >> 1;
        // cout << l << ' ' << r << ' ' << mid << endl;
        if(cmp(mid)){
            l = mid+1; 
        }else{
            r = mid-1; ④
            ans = mid; ⑤
        }
    }
    // cout << l << ' ' << r << ' ' << mid << endl;
    cout << ans << endl;
    return 0;
}

DeBug

①:等号取不取的问题。

之前写的代码是 return ans >= m; 这里仔细思考一下。我的代码假设的是如果不符合要求就返回1,符合要求就返回0,那么 ans == m 很显然是符合条件的,如果也返回1,那就被算成错误的了。

②:左右端点的问题

其实这个地方比较无关紧要。右端点取总和,但是我的左端点一开始写的是取0,后来改成了a的最大值。其实我的cmp判断函数里面对这个东西有特判,所以这一句在DeBug的时候没啥用。

③④:返回条件的问题

二分模板掌握不熟练,打死好了。

⑤:答案记录的问题

只有mid的值返回0(也就是mid满足要求)的时候才能记录到ans,我之前不管返回几都记录,导致我答案不对。后来才放到else里面。

posted @ 2020-03-24 22:27  CYC的幸福生活  阅读(176)  评论(0编辑  收藏  举报