算法 数组中的逆序对-(归并排序+递归回溯+双指针)

news/2024/5/17 20:14:04 标签: 逆序对, 归并排序, 双指针, 递归回溯

牛客网: BM20

题目: 求出数组中逆序对总数

思路: 使用归并排序思路,先分裂,再合并,合并的时候,左半段有序,右半段有序,如果左半段某个值大于右半段某个值 data[i] > data[j], 则可通过j与右半段起始坐标之间的距离算出共有多少个比data[i]小,即这一小段的逆序对的数量;在复制数组dataCopy中一直按照比较的结果来更新数值,作为回溯时的data使用。

注意: 中间点 mid = (left+right)/2,需要归到左半段中,否则递归时使用inverse(left, mid-1), 即下一层right=mid-1, 存在right < left情况,如果这样的话,则需要在递归前添加判断单独处理,否则会栈溢出。

代码:

package main
// import "fmt"

/**
 * 代码中的类名、方法名、参数名已经指定,请勿修改,直接返回方法规定的值即可
 *
 * 
 * @param nums int整型一维数组 
 * @return int整型
*/
const BASE = 1000000007

func InversePairsCount(data, dataCopy []int, left, right int) int {
    if left < right {
        mid := left + (right - left) >> 1
        leftCount := InversePairsCount(dataCopy, data, left, mid)
        rightCount := InversePairsCount(dataCopy, data, mid+1, right)
        count := 0
        i := mid
        j := right
        idx := right
        for i >= left && j > mid {
            if data[i] > data[j] {
                count += j - mid
                dataCopy[idx] = data[i]
                idx--
                i--
            } else {
                dataCopy[idx] = data[j]
                idx--
                j--
            }
        }
        for i >= left {
            dataCopy[idx] = data[i]
            idx--
            i--
        }
        for j > mid {
            dataCopy[idx] = data[j]
            idx--
            j--
        }
        return (count + leftCount + rightCount) % BASE
    } else{
        dataCopy[left] = data[left]
        return 0
    }
}

func InversePairs( nums []int ) int {
    // write code here
    if len(nums) == 0 {
        return 0
    }
    dataCopy := make([]int, len(nums))
    for i := 0; i < len(nums); i++ {
        dataCopy[i] = nums[i]
    }
    left, right := 0, len(nums) - 1
    count := InversePairsCount(nums, dataCopy, left, right)
    return count % BASE
}


http://www.niftyadmin.cn/n/5043157.html

相关文章

全套办公软件Office 2019 mac专业版功能

Microsoft office 2019 Beta for Mac 是一款办公软件套装&#xff0c;它包含常用的办公应用程序&#xff0c;如 Word、Excel、PowerPoint 和 Outlook 等。office 2019 Beta 版本是一个测试版本&#xff0c;旨在让用户提前体验下一个版本的 office 套件&#xff0c;以便用户可以…

从零开始:使用Rust语言在STM32F4处理器上实现VGA风格视频输出的完整指南

第一部分&#xff1a;介绍与背景 1. 介绍 在当今的技术世界中&#xff0c;嵌入式系统和微控制器在各种应用中都发挥着重要作用。STM32F4是其中的佼佼者&#xff0c;它是一个高性能的微控制器&#xff0c;广泛应用于各种嵌入式解决方案中。在本文中&#xff0c;我们将探讨如何使…

ubuntu samba文件共享服务器搭建

目的&#xff1a; 为了实现Android源码在ubuntu的编译&#xff0c;在windows上进行源码的修改和验证&#xff0c;需要在ubuntu系统上搭建共享文件夹&#xff0c;这里将ubuntu的/home/用户/路径下的所有内容共享&#xff0c;方法如下 ubuntu端&#xff1a; 一、samba安装 sud…

Oracle 透明数据加密(TDE)的常见任务

环境准备 一个容器数据库&#xff0c;带一个PDB&#xff1a;orclpdb1。 目前没有进行任何加密设置。 SQL> show pdbs;CON_ID CON_NAME OPEN MODE RESTRICTED ---------- ------------------------------ ---------- ----------2 PDB$SEED …

RabbitMQ里的几个重要概念

RabbitMQ中的一些角色&#xff1a; publisher&#xff1a;生产者consumer&#xff1a;消费者exchange个&#xff1a;交换机&#xff0c;负责消息路由&#xff0c;接受生产者发送的消息&#xff0c;把消息发送到一个或多个队列里queue&#xff1a;队列&#xff0c;存储消息virt…

李航老师《统计学习方法》第2章阅读笔记

感知机&#xff08;perceptron&#xff09;时二类分类的线性分类模型&#xff0c;其输入为实例的特征向量&#xff0c;输出为实例的类别&#xff0c;取1和-1二值。感知机对应于输入空间&#xff08;特征空间&#xff09;中将实例划分为正负两类的分离超平面 想象一下在一个平面…

Matlab图像处理-模式识别方法

模式识别方法 模式分类或模式匹配的方法有很多&#xff0c;总体分为四大类&#xff1a; 以数据聚类的监督学习方法&#xff1b; 以统计分类的无监督学习方法&#xff1b; 通过对基本单元判断是否符合某种规则的结构模式识别方法&#xff1b; 可同时用于监督或者非监督学习…

java Spring Boot2.7实现一个简单的爬虫功能

首先 我们要在 pom.xml 中注入Jsoup 这是一个简单的java爬虫框架 <dependency><groupId>org.jsoup</groupId><artifactId>jsoup</artifactId><version>1.14.1</version> </dependency>然后这里我们直接用main吧 做简单一点 我…