数组——数组中的逆序对

【剑指offer】数组中的逆序对 思路:最简单的方法是顺序数组,将每个数字与后面的比较,统计逆序对的个数,这种方法的时间复杂度为O(n*n),这种方法写出的代码在九度OJ上测试,会超时。剑指offer给出了归并排序的思路,这个有点难想到啊,也可能是我太弱了,根本没往这方面想!理解了思路,就不难了,将数组划分成两个子数组,再将子数组分别划分成两个子数组,统计每个子数组内的逆序对个数,并将其归并排序,再统计两个子数组之间的逆序对个数,并进行归并排序。这就是归并排序的变种,在归并排序代码的基础上稍作改进即可。 合理还要注意一点:全局变量c 阅读详情

1,问题描述

在数组中的两个数字,如果前面一个数字大于后面的数字,则这两个数字组成一个逆序对。输入一个数组,求出这个数组中的逆序对的总数P。并将P对1000000007取模的结果输出。 即输出P%1000000007。

  • 输入描述:题目保证输入的数组中没有的相同的数字,数组大小的范围:
    • 对于%50的数据,size<=10^4
    • 对于%75的数据,size<=10^5
    • 对于%100的数据,size<=2*10^5

2,解题思路

有两种解题思路:
(1)遍历整个数组,将遍历元素与其之后的元素一一比较,有小于其的,逆序对数加1。这种方法想法简单,但是复杂度过高,只能通过50%。
(2)转自牛客, 归并排序的改进。
把数据分成前后两个数组(递归分到每个数组仅有一个数据项),合并数组。合并时,出现后面的数组值array[j]小于前面数组值array[i]时;则后面数组array[mid+1]~array[j]都是小于array[i]的,count += (j-mid)。参考剑指Offer,但是感觉剑指Offer归并过程少了一步拷贝过程。还有就是测试用例输出结果比较大,需要对每次返回的count mod(1000000007)求余。

3,源码

(1)第一种方法源码

public class Solution {
    public int InversePairs(int [] array) {
        int n = array.length;
        int count = 0;
        for(int i = 0;i<n-1;i++){
            for(int j = i+1; j<n; j++){
                if(array[j] < array[i]){
                    count++;
                }
            }
        }
        return count%1000000007;
    }
}

(2)第二种方法源码

public class Solution {
    public int InversePairs(int [] array) {
        int n = array.length;
        if(n <= 1){
            return 0;
        }
        int[] copy = new int[n];
        //for(int i=0;i<n;i++){
        //    copy[i] = array[i];
        //}
        int count = InversePairsCore(array,copy,0,n-1);
        return count;
    }
    
    public static int InversePairsCore(int[] array, int[] copy, int start, int end){
        if(start>=end){
            return 0;
        }
        int mid = (start+end)>>1;
        int count = 0;
        //递归的过程,即,不断拆解、统计逆序对、排序和合并的过程。
        int leftCount = InversePairsCore(array,copy,start,mid)%1000000007;
        int rightCount = InversePairsCore(array,copy,mid+1,end)%1000000007;
        int i = mid;
        int j = end;
        int copyIndex = end;
        //从左右子数组的最后一个元素开始对比,直到遍历完其中的一个子数组
        while(i>=start && j>mid){
            if(array[i] > array[j]){
                count += j-mid;
                //每比较一次,copy数组确定一个最终元素。
                copy[copyIndex--] = array[i--];
                if(count>=1000000007){
                    count%=1000000007;
                }
            }else{
                copy[copyIndex--] = array[j--];
            }
        }
        //接下来的两个循环是将左右子数组中剩余的有序部分拷贝到copy数组。
        while(i>=start){
            copy[copyIndex--] = array[i--];
        }
        while(j>mid){
            copy[copyIndex--] = array[j--];
        }
        //统计完逆序对后,将原始数组的该部分变成有序数组,即,合并、排序的过程。
        for(int k = start; k<=end;k++){
            array[k] = copy[k];
        }
        
        return (leftCount+rightCount+count)%1000000007;
    }
}

微信扫码关注:挑灯看剑王知事
在这里插入图片描述

算法设计之分治思想(求数组的逆序对) 在数组中的两个数字,如果前面一个数字大于后面的数字,则这两个数字组成一个逆序对。输入一个数组,求出这个数组中的逆序对的总数。 示例 1: 输入: [7,5,6,4] 输出: 5 限制: 0 <= 数组长度 <= 50000 首先最容易想到的是暴力解法。 方法一:暴力解法(超时) 使用两层 for 循环枚举所有的数对,逐一判断是否构成逆序关系。 参考代码 1: java private static int reversePairs(int[] nums) { // TODO Auto-generated method stub int res = 0; int len = num 立即下载

相关推荐

tkinter表格进阶:5分钟实现CSV数据可视化编辑界面(含右键菜单配置)

本文详细介绍了如何使用Python的tkintertable库快速构建CSV数据可视化编辑界面。通过导入导出CSV数据、深度定制右键菜单(如复制、插入行、删除行)以及实现单元格验证等进阶功能,开发者能在5分钟内创建一个可嵌入自动化流程的专业级桌面数据编辑工具,显著提升数据处理效率。

929

归并排序模板(非递归、求逆序对)

剑指 Offer 51. 数组中的逆序对 在数组中的两个数字,如果前面一个数字大于后面的数字,则这两个数字组成一个逆序对。输入一个数组,求出这个数组中的逆序对的总数。 示例 1: 输入: [7,5,6,4] 输出: 5 限制: 0 <= 数组长度 <= 50000 class Solution { private int ans=0; private void merge(int[] nums, int low, int mid, int high) { .

weixin_42324579的博客 621

基于IC555的PWM信号发生器设计:从原理到电机调速与LED调光应用

脉冲宽度调制(PWM)是一种通过调节数字脉冲宽度来控制模拟信号电平的核心技术,其原理在于固定频率下改变高电平占空比,从而等效调节平均电压或功率。这项技术因其高效率、低损耗的特点,在电机调速、LED调光、开关电源等工程领域具有重要价值。本文聚焦于利用经典IC555定时器芯片构建PWM信号发生器,通过分析其无稳态工作模式及改进型电路设计,实现了占空比独立可调且频率稳定的信号输出。文中结合电机驱动与LED调光等具体应用场景,详细阐述了电路参数计算、元件选型、PCB设计及常见问题排查等实践要点,为电子爱好者与工程师

weixin_30342363的博客 396

数组中的逆序对

数组中的逆序对题目描述   基础的排序算法,尤其是常见的几种特殊的排序算法,一定要深刻理解,记住特性,甚至要能写出代码。 题目描述   在数组中的两个数字,如果前面一个数字大于后面的数字,则这两个数字组成一个逆序对。输入一个数组,求出这个数组中的逆序对的总数P。并将P对1000000007取模的结果输出。 即输出P%1000000007。                              ...

August-us的博客 1万+

从0到1做AI漫剧:即梦+豆包+剪映+红果全流程实战

AI视频生成正在重塑内容创作的生产方式,它让原本高门槛的影视制作,变成了一条由文本、画面、剪辑与分发环节协同的流水线。理解其底层原理,在于将大模型的语义理解、图像生成与视频合成能力,与工程化的流程管理相结合,从而实现从创意到成片的自动化输出。这种技术的价值,不仅体现在降低制作成本,更在于让个人创作者能够独立完成高质量短剧,并快速迭代内容。在短剧、短视频、广告营销等场景中,利用即梦生成画面、豆包编写剧本、剪映完成剪辑、红果进行分发的组合,已成为一种被广泛验证的实践路径。本文聚焦AI漫剧制作,从环境准备、分镜设

weixin_34072637的博客 380

DRM驱动架构浅析-上(DRM基础概要与U-Boot阶段驱动解析)

本文主要探讨了Rockchip平台的DRM显示驱动架构及其在U-Boot阶段的实现。

一路寒风身如絮,命海沉浮客独行 1761

算法的学习笔记—数组中的逆序对(牛客JZ51)

逆序对问题是一个经典的算法问题,借助归并排序可以将其优化至Onlog⁡nOnlogn的时间复杂度。通过在归并排序的过程中适时地统计逆序对,我们可以有效地解决这个问题。😁热门专栏推荐想学习vue的可以看看这个java基础合集数据库合集redis合集nginx合集linux合集手写机制微服务组件spring_尘觉springMVCmybits🤔欢迎大家加入我的社区尘觉社区文章到这里就结束了,如果有什么疑问的地方请指出,诸佬们一起来评论区一起讨论😁。

业精于勤,荒于嬉 1860

Python全栈入门到实战【基础篇 04】核心基础:变量与4种基础数据类型(int/float/str/bool)

本文介绍了Python编程中的变量和四种基础数据类型,作为后续所有语法的入门前提。变量是数据的“容器”,解决数据复用问题,而数据类型决定数据能进行的操作。文章详细讲解了变量的定义语法、命名规则(强制语法和推荐风格)、赋值与修改原理,并通过实操示例展示其应用场景。正确使用变量可以提升代码复用性、简化修改并增强可读性,是编程效率的核心原则。掌握这些基础知识能避免90%的新手语法错误,为学习更复杂的Python语法打下坚实基础。

那些看似不起波澜的日复一日,会在某天让你看到坚持的意义 4307

【数组】 数组中的逆序对

题目描述 在数组中的两个数字,如果前面一个数字大于后面的数字,则这两个数字组成一个逆序对。输入一个数组,求出这个数组中的逆序对的总数P。并将P对1000000007取模的结果输出。 即输出P%1000000007 输入描述: 题目保证输入的数组中没有的相同的数字 数据范围: 对于%50的数据,size<=10^4 对于%75的数据,size<=10^5 对于%100的数据...

永生只是一场幻梦 2721

一次请求穿过的六道关卡:微服务基础组件的通信与IO、事件驱动、负载均衡、服务路由、API网关与配置协调

微服务的稳定性往往取决于看不见的基础组件。本文跟随一次下单请求,依次穿过API网关、服务路由、负载均衡与服务通信,再沿事件分支扇出,并从控制面审视配置中心。通信层剖析握手成本、连接复用、epoll与主从Reactor、心跳判活、退避抖动、截止时间与重试预算;事件层讲解编舞与编排、事务发件箱和幂等消费;均衡与路由对比静态与动态算法、路由链、全链路灰度与同区保底;网关讨论过滤器链与限流算法;配置部分给出四类配置、长轮询与共识协调,最后归纳五道防线。文中关键数据均来自可在Java8运行的演示程序。

曾经“等你生日那天”都遥远得像未来,如今却可欢愉的挥手说“下个十年见” 172万+

File does not exist: /user/anonymous/.staging/job_1628851608378_6064/报错问题解决

user/admin/.staging/job_1571397171638_0001/job_1571397171638_0001_1.jhist 所以为什么没有下发,这里面jhist,只是被引发的错误,它还不是根本的错误。看到上面错误,我们就可以判断,这是网络问题,然而网络无非是ip地址,防火墙,端口,hosts等。我们正常的hosts是这样的。在回头复盘想想,我们找不到jhist,跟我们的网络问题二者是很难找到关联的,所以大家在遇到问题的时候,一定多排查和思考,而不是看到一个错误,就以为是它的问题。

石榴姐yyds 2169

python 数组中的逆序对

''' 在数组中的两个数字,如果前面一个数字大于后面的数字,则这两个数字组成一个逆序对。输入一个数组,求出这个数组中的逆序对的总数P。并将P对1000000007取模的结果输出。 即输出P%1000000007 输入描述: 题目保证输入的数组中没有的相同的数字 数据范围: 对于%50的数据,size<=10^4 对于%75的数据,size<=10^5 对于%100的数...

WYXHAHAHA123的博客 1769

【嵌入式Linux驱动开发】二十四、Linux I2C 驱动上手尝试

  人的前程关于眼界、关乎格局。   志之所趋,无远弗届,穷山复海不能限也;   志之所向,无坚不入,锐兵精甲不能御也。 一、I2C驱动框架简介   Linux内核将 I2C 驱动分为两部分: ①、 I2C 总线驱动, I2C 总线驱动就是 SOC 的 I2C 控制器驱动,也叫做 I2C 适配器驱动。 ②、 I2C 设备驱动, I2C 设备驱动就是针对具体的 I2C 设备而编写的驱动。 1....

悟已往之不谏 知来者之可追 1068

数组之数组中的逆序对

1.本题知识点    归并排序 2. 题目描述   在数组中的两个数字,如果前面一个数字大于后面的数字,则这两个数字组成一个逆序对。输入一个数组,求出这个数组中的逆序对的总数P。并将P对1000000007取模的结果输出。 即输出P%1000000007 3. 思路    ① 归并排序,不会的请跳到我的基础算法博客查看。    ② 归并过程中,排序的同时记录逆序对的个数。    Java版本:...

守得云开见月明 367

Devexpress16.2.6破解工具

Devexpress16.2.6破解工具Devexpress16.2.6破解工具Devexpress16.2.6破解工具Devexpress16.2.6破解工具

蓝牙模块HM-10手册

蓝牙模块HM-10手册,该手册对蓝牙模块HM-10进行了详细的介绍和使用方法以及一些AT指令。

剑指offer47_数组中的逆序对

数组中的逆序对

君鼎的博客 823

假人有限元模型

假人模型,车辆碰撞假人有限元模型,适合做乘员安全的研究者利用

【分治】数组中的逆序对

本文介绍了两种基于归并排序的解法来计算数组中的逆序对数量。第一种思路利用升序排序,在合并过程中统计左区间大于右区间的元素个数;第二种思路通过降序排序,统计右区间小于左区间的元素个数。两种方法均通过分治策略将时间复杂度优化至O(nlogn),避免了暴力解法的O(n²)复杂度。代码实现中展示了升序合并时的关键判断逻辑,通过临时数组辅助完成排序与统计。该问题展示了归并排序在统计特定顺序对时的巧妙应用。

lirendada的博客 1378

大中型超市收银系统(可直接运行)

光步前台收银系统系统功能:商品销售、商品退货、挂单、收银员权限、会员销售、单品取消、整单取消、商品查询、脱机销售、脱机数据上传,基本资料下载,开钱箱、小票打印、收款结算,支持多币种付款方式(现金、储值卡、礼券、微信等),支持多种促销。运行环境:.net 4.0登陆信息用户名:1001 密码:123456内置商品信息,商品编码可输入00001000 - 00010000,测试效果相关功能键F5 结算 F9挂单 F11商品查询 F8退货 Insert单品取消 Del整单取消 F12开钱箱F2 会员 Ctrl+Z退出系统 Home 锁屏 相关源码待公开

上一篇: LR和SVM的联系和区别
下一篇: 数组——数组中只出现一次的数字
Manduner_TJU
博客等级 码龄9年 157粉丝 131原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

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

抵扣说明:

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

余额充值