力扣刷题——数组(2)

  1. 将每个元素替换为右侧最大元素
给你一个数组 arr ,请你将每个元素用它右边最大的元素替换,
如果是最后一个元素,用 -1 替换。
完成所有替换操作后,请你返回这个数组。

示例:
输入:arr = [17,18,5,4,6,1]
输出:[18,6,6,6,1,-1]

提示:
1 <= arr.length <= 10^4
1 <= arr[i] <= 10^5

思路1模拟,从左到右
这个思路应该是最容易想到的,两层循环,外层循环从左到右,内循环找到当前位置右边最大的元素,然后填入到当前位置。

int* 
replaceElements(int* arr, int arrSize, int* returnSize){
    *returnSize = arrSize;
    for(int i=0; i<arrSize-1; i++){
        int max = arr[i+1];
        for(int j=i+1; j<arrSize; j++){
            if(arr[j]>max) max = arr[j];
        } arr[i] = max;
    } arr[arrSize-1] = -1;
    return arr;
}

思路2倒序,从右到左
从后面往前面遍历,一次遍历即可实现:
维护一个max变量,初始值为-1
每次遍历将max的值填入当前位置,并比较该位置原本值与max值的大小
如果原本值大于max值,则更新max值
比如[18,2,9,3,4,5,6,1,2]…稍作模拟即可理解。

int* 
replaceElements(int* arr, int arrSize, int* returnSize){
    *returnSize = arrSize;
    for(int i=arrSize-1, max=-1; i>0-1; i--){
        int temp = arr[i];
        arr[i] = max;
        if(temp>max) max = temp;
    } return arr;
}

.
.
.

  1. 数组拆分 I
给定长度为 2n 的数组, 你的任务是将这些数分成 n 对, 
例如 (a1, b1), (a2, b2), ..., (an, bn) ,使得从1 到 n 的 min(ai, bi) 总和最大

示例 1:
输入: [1,4,3,2]
输出: 4
解释: n 等于 2, 最大总和为 4 = min(1, 2) + min(3, 4).

提示:
n 是正整数,范围在 [1, 10000].
数组中的元素范围在 [-10000, 10000].

思路排序,index为偶数的各项之和
由于要求每对min之和总数要最大,所以我们min选取的每对数字,
要保证损耗最小,比如min(5,3)=3,这里的损耗就是5-3=2
我们要尽可能减小这种损耗,不要造成不必要的浪费
所以,如果我们把数组排序起来,然后两两取对,
则每对元素之间差距最小,那么总体的损耗也是最小的。
所以对于这道题,我们只需要排序之后求偶数下标的各项之和即可

int 
cmpfun(const void * a, const void * b){
    return *(int*)a-*(int*)b;
}

int 
arrayPairSum(int* nums, int numsSize){
    int retsum = 0;
    qsort(nums, numsSize, sizeof(nums[0]), cmpfun);
    for(int i=0; i<numsSize; i+=2){
        retsum+=nums[i];
    } return retsum;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值