草庐IT

代码随想录算法训练营第二天 | LeetCode 977.有序数组的平方、209.长度最小的子数组、59.螺旋矩阵II

Ye_memory 2024-01-22 原文

目录

一、今日心得感悟

        1、数组从小到大排序

①冒泡法--时间复杂度:O(nlogn)

②使用排序函数qsort--时间复杂度:O(nlogn)       

③两端->中间(双指针法) --时间复杂度:O(n)

④归并排序(双指针法) --时间复杂度:O(n)

        2、二维数组的访问及动态分配 

        3、时间复杂度

        4、滑动窗口

二、题目

977.有序数组的平方

        题目链接

        想法

        代码实现(未看视频/题解)

        遇到的问题

209.长度最小的子数组

        题目链接

        想法

        代码实现(未看视频/题解)

        遇到的问题

59.螺旋矩阵II

        题目链接

        想法

        代码实现(未看视频/题解)

        遇到的问题

附录


一、今日心得感悟

        1、数组从小到大排序

冒泡法--时间复杂度:O(nlogn)

②使用排序函数qsort--时间复杂度:O(nlogn)       

使用方法:

qsort(array, arraySize, sizeof(a[0]), cmp);

int cmp(const void* a1, const void* b1)

{

        int a = *(int*)a1;

        int b = *(int*)b1;

        return a - b;       

}

两端->中间(双指针法) --时间复杂度:O(n)

思路与算法

        同样地,我们可以使用两个指针分别指向位置 0 和 n−1,每次比较两个指针对应的数,选择较大的那个逆序放入答案并移动指针。

        这种方法无需处理某一指针移动至边界的情况,读者可以仔细思考其精髓所在。

归并排序(双指针法) --时间复杂度:O(n)

思路与算法

        如果我们能够找到数组中负数与非负数的分界线,那么就可以用类似「归并排序」的方法了。

        具体地,我们设neg为数组中负数与非负数的分界线,也就是说:

array[0] ~ array[neg] 均为负数;

array[neg + 1] ~ array[n - 1] 均为负数

        当我们将数组中的数平方后,那么array[0] ~ array[neg]单调递减,array[neg + 1] ~ array[n - 1] 单调递增。

        由于我们得到了两个已经有序的子数组,因此就可以使用归并的方法进行排序了。

        具体地,使用两个指针分别指向位置 neg 和 neg + 1 ,每次比较两个指针对应的数,选择较小的那个放入答案并移动指针。当某一指针移至边界时,将另一指针还未遍历到的数依次放入答案。 

        2、二维数组的访问及动态分配 

 未整理完,整理过程参考的资料如下:

1、用指针访问二维数组

(1条消息) 用指针访问二维数组_指针指向二维数组_宗谷.的博客-CSDN博客

2、二维数组及其动态内存分配

(1条消息) 二维数组及其动态内存分配_二维数组动态分配内存_Baymaxly的博客-CSDN博客

        3、时间复杂度

O(1) < O(logn) < O(n) < O(nlogn) < O() < O() < O() < O() < O(

        4、滑动窗口

滑动窗口适用范围:

顺序不可变的数组Array中找 连续子数组 array

 

二、题目

977.有序数组的平方

        题目链接

977. 有序数组的平方 - 力扣(LeetCode)

        想法

法1:先得到新数组,在对新数组进行排序(qsort)

时间复杂度:O(nlogn)

法2:

 时间复杂度:O(n)

        代码实现(未看视频/题解)

/**
 * Note: The returned array must be malloced, assume caller calls free().
 */
int cmp(const void*a1, const void*b1){
    int a = *(int*)a1, b = *(int*)b1;
    return a - b;
}

int* sortedSquares(int* nums, int numsSize, int* returnSize){
    int *ret = (int*)malloc(numsSize * sizeof(int));
    *returnSize = numsSize;
    for(int i = 0; i < numsSize; i++){
        ret[i] = nums[i] * nums[i];
    }
    qsort(ret, numsSize, sizeof(int), cmp);
    return ret;
}

        遇到的问题

未能在时间复杂度为O(n)时做出解答(对于原数组有负有正的排序未成功)

209.长度最小的子数组

        题目链接

209. 长度最小的子数组 - 力扣(LeetCode)

        想法

1、先把题目做出来(不考虑时间复杂度的问题)

2、若超时,则重新思考---“滑动窗口”

        代码实现(未看视频/题解)

1、第一次实现的代码超出了时间限制---时间复杂度:O(n²)

int minSubArrayLen(int target, int* nums, int numsSize){
    int ret = 0, len = 1, flag = 0, cnt = 0;
    long long sum = 0;
    for(int i = 0; i < numsSize; i++){
        sum += nums[i];
        if(sum >= target){
            flag = 1;
            cnt++;
            ret = 1;
        }
        else if(i < (numsSize - 1)){
            for(int j = i + 1; j < numsSize; j++){
                sum += nums[j];
                len++;
                if(sum >= target){
                    flag = 1;
                    cnt++;
                    if(cnt == 1){
                        ret = len;
                    }
                    if(ret > len){
                        ret = len;
                    }
                    break;
                }
            }
        }
        sum = 0;
        len = 1;
    }
    return ret;
}

2、第二次实现的代码(滑动窗口)---时间复杂度:O(n)

int minSubArrayLen(int target, int* nums, int numsSize){
    int index1 = 0, index2 = 0;
    int len, ret = 0, cnt = 0;
    long long sum = 0;
    while(index1 < numsSize){
        // 求len
        len = index2 - index1 + 1;
        // 求sum
        if(index2 == index1)
            sum += nums[index1];
        else if(index2 <= (numsSize - 1)) 
            sum += nums[index2];
        // 判断
        here:
        if(sum < target){
            if(index2 < (numsSize - 1))
                index2++;
            else
                break;
        }
        else{
            // 得到ret
            cnt++;
            if(cnt == 1)
                ret = len;
            else if(ret > len){
                ret = len;
            }
            sum -= nums[index1];
            index1++;
            len = index2 - index1 + 1;
            goto here;
        }
    }                           
    return ret;                          
}

        遇到的问题

未看题解时,只能想出O()算法。 

59.螺旋矩阵II

        题目链接

59. 螺旋矩阵 II - 力扣(LeetCode)

        想法

此题以前做过,方法是:

从左到右

从上到下

从右到左

从下到上

依次给数组赋值

        代码实现(未看视频/题解)

/**
 * Return an array of arrays of size *returnSize.
 * The sizes of the arrays are returned as *returnColumnSizes array.
 * Note: Both returned array and *columnSizes array must be malloced, assume caller calls free().
 */
int** generateMatrix(int n, int* returnSize, int** returnColumnSizes){

    int** ret = malloc(sizeof(int*) * n);
    *returnSize = n;
    *returnColumnSizes = malloc(sizeof(int) * n);
    for (int i = 0; i < n; i++) {
        ret[i] = malloc(sizeof(int) * n);
        (*returnColumnSizes)[i] = n;
    }

    int left = 0, right = n - 1, up = 0, down = n - 1;
    int i = 0, j = 0, num = 1;
    while(left <= right && up <= down){
        // 左 -> 右
        for(j = left; j <= right; j++){
            *(*(ret + up) + j) = num++;
        }
        up++;
        // 上 -> 下
        for(i = up; i <= down; i++){
            *(*(ret + i) + right) = num++;
        }
        right--;
        // 右 -> 左
        for(j = right; j >= left; j--){
            *(*(ret + down) + j) = num++;
        }
        down--;
        // 下 -> 上
        for(i = down; i >= up; i--){
            *(*(ret + i) + left) = num++;
        }
        left++;
    }
    return ret;
}

        遇到的问题

有一种想法,叫做leetcode的想法……

“int left = 0……”上面的代码是看题解后修改的,未看题解前:

认为returnSize是n²,结果题解是n

附录

思路与算法的具体内容见下:

作者:LeetCode-Solution
链接:https://leetcode.cn/problems/squares-of-a-sorted-array/solution/you-xu-shu-zu-de-ping-fang-by-leetcode-solution/
来源:力扣(LeetCode)
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。 

有关代码随想录算法训练营第二天 | LeetCode 977.有序数组的平方、209.长度最小的子数组、59.螺旋矩阵II的更多相关文章

  1. ruby-on-rails - unicode 字符串的长度 - 2

    在我的Rails(2.3,Ruby1.8.7)应用程序中,我需要将字符串截断到一定长度。该字符串是unicode,在控制台中运行测试时,例如'א'.length,我意识到返回了双倍长度。我想要一个与编码无关的长度,以便对unicode字符串或latin1编码字符串进行相同的截断。我已经了解了Ruby的大部分unicode资料,但仍然有些一头雾水。应该如何解决这个问题? 最佳答案 Rails有一个返回多字节字符的mb_chars方法。试试unicode_string.mb_chars.slice(0,50)

  2. ruby-on-rails - 在 Ruby 中循环遍历多个数组 - 2

    我有多个ActiveRecord子类Item的实例数组,我需要根据最早的事件循环打印。在这种情况下,我需要打印付款和维护日期,如下所示:ItemAmaintenancerequiredin5daysItemBpaymentrequiredin6daysItemApaymentrequiredin7daysItemBmaintenancerequiredin8days我目前有两个查询,用于查找maintenance和payment项目(非排他性查询),并输出如下内容:paymentrequiredin...maintenancerequiredin...有什么方法可以改善上述(丑陋的)代

  3. ruby - 如何以所有可能的方式将字符串拆分为长度最多为 3 的连续子字符串? - 2

    我试图获取一个长度在1到10之间的字符串,并输出将字符串分解为大小为1、2或3的连续子字符串的所有可能方式。例如:输入:123456将整数分割成单个字符,然后继续查找组合。该代码将返回以下所有数组。[1,2,3,4,5,6][12,3,4,5,6][1,23,4,5,6][1,2,34,5,6][1,2,3,45,6][1,2,3,4,56][12,34,5,6][12,3,45,6][12,3,4,56][1,23,45,6][1,2,34,56][1,23,4,56][12,34,56][123,4,5,6][1,234,5,6][1,2,345,6][1,2,3,456][123

  4. ruby - 多次弹出/移动 ruby​​ 数组 - 2

    我的代码目前看起来像这样numbers=[1,2,3,4,5]defpop_threepop=[]3.times{pop有没有办法在一行中完成pop_three方法中的内容?我基本上想做类似numbers.slice(0,3)的事情,但要删除切片中的数组项。嗯...嗯,我想我刚刚意识到我可以试试slice! 最佳答案 是numbers.pop(3)或者numbers.shift(3)如果你想要另一边。 关于ruby-多次弹出/移动ruby​​数组,我们在StackOverflow上找到一

  5. ruby - 将数组的内容转换为 int - 2

    我需要读入一个包含数字列表的文件。此代码读取文件并将其放入二维数组中。现在我需要获取数组中所有数字的平均值,但我需要将数组的内容更改为int。有什么想法可以将to_i方法放在哪里吗?ClassTerraindefinitializefile_name@input=IO.readlines(file_name)#readinfile@size=@input[0].to_i@land=[@size]x=1whilex 最佳答案 只需将数组映射为整数:@land边注如果你想得到一条线的平均值,你可以这样做:values=@input[x]

  6. ruby - 通过 erb 模板输出 ruby​​ 数组 - 2

    我正在使用puppet为ruby​​程序提供一组常量。我需要提供一组主机名,我的程序将对其进行迭代。在我之前使用的bash脚本中,我只是将它作为一个puppet变量hosts=>"host1,host2"我将其提供给bash脚本作为HOSTS=显然这对ruby​​不太适用——我需要它的格式hosts=["host1","host2"]自从phosts和putsmy_array.inspect提供输出["host1","host2"]我希望使用其中之一。不幸的是,我终其一生都无法弄清楚如何让它发挥作用。我尝试了以下各项:我发现某处他们指出我需要在函数调用前放置“function_”……这

  7. ruby - 检查数组是否在增加 - 2

    这个问题在这里已经有了答案:Checktoseeifanarrayisalreadysorted?(8个答案)关闭9年前。我只是想知道是否有办法检查数组是否在增加?这是我的解决方案,但我正在寻找更漂亮的方法:n=-1@arr.flatten.each{|e|returnfalseife

  8. ruby - 如果指定键的值在数组中相同,如何合并哈希 - 2

    我有一个这样的哈希数组:[{:foo=>2,:date=>Sat,01Sep2014},{:foo2=>2,:date=>Sat,02Sep2014},{:foo3=>3,:date=>Sat,01Sep2014},{:foo4=>4,:date=>Sat,03Sep2014},{:foo5=>5,:date=>Sat,02Sep2014}]如果:date相同,我想合并哈希值。我对上面数组的期望是:[{:foo=>2,:foo3=>3,:date=>Sat,01Sep2014},{:foo2=>2,:foo5=>5:date=>Sat,02Sep2014},{:foo4=>4,:dat

  9. ruby - 在 Ruby 中用键盘诅咒数组浏览 - 2

    我正在尝试在Ruby中制作一个cli应用程序,它接受一个给定的数组,然后将其显示为一个列表,我可以使用箭头键浏览它。我觉得我已经在Ruby中看到一个库已经这样做了,但我记不起它的名字了。我正在尝试对soundcloud2000中的代码进行逆向工程做类似的事情,但他的代码与SoundcloudAPI的使用紧密耦合。我知道cursesgem,我正在考虑更抽象的东西。广告有没有人见过可以做到这一点的库或一些概念证明的Ruby代码可以做到这一点? 最佳答案 我不知道这是否是您正在寻找的,但也许您可以使用我的想法。由于我没有关于您要完成的工作

  10. ruby - 匹配大写字母并用后续字母填充,直到一定的字符串长度 - 2

    我有一个驼峰式字符串,例如:JustAString。我想按照以下规则形成长度为4的字符串:抓取所有大写字母;如果超过4个大写字母,只保留前4个;如果少于4个大写字母,则将最后大写字母后的字母大写并添加字母,直到长度变为4。以下是可能发生的3种情况:ThisIsMyString将产生TIMS(大写字母);ThisIsOneVeryLongString将产生TIOV(前4个大写字母);MyString将生成MSTR(大写字母+tr大写)。我设法用这个片段解决了前两种情况:str.scan(/[A-Z]/).first(4).join但是,我不太确定如何最好地修改上面的代码片段以处理最后一种

随机推荐