差分

一维差分

"""
# 查分适用场景
给你一串长度为n的数列a1,a2,a3......an,要求对a[L]~a[R]进行m次操作:
操作一:将a[L]~a[R]内的元素都加上P
操作二:将a[L]~a[R]内的元素都减去P

[参考](https://www.jianshu.com/p/fcb68475b5e4)

查分是前缀和的逆运算
原数组:a1, a2, a3, a4
查分数组:b1 = a1
        b2 = a2 - a1
        b3 = a3 - a2
        b4 = a4 - a3
即满足:a1 = b1
       a2 = b1 + b2
       a3 = b1 + b2 + b3
       a4 = b1 + b2 + b3 + b4
"""

package main

import (
    "bufio"
    "fmt"
    "os"
    "strconv"
    "strings"
)

/*
差分是前缀和的逆运算
原数组:a1, a2, a3, a4
查分数组:b1 = a1
        b2 = a2 - a1
        b3 = a3 - a2
        b4 = a4 - a3
即满足:a1 = b1
       a2 = b1 + b2
       a3 = b1 + b2 + b3
       a4 = b1 + b2 + b3 + b4
*/
var (
    a []int
    b []int
)

func add(l, r, p int) {
    b[l-1] += p
    if r < len(b) {
        b[r] -= p
    }
}

// 对于差分只有一个操作
func main() {
    var reader = bufio.NewReader(os.Stdin)
    var x = readArray(reader)
    a = readArray(reader)
    b = make([]int, x[0])

    // 构造差分数组
    // 题目将1作为下标开始
    for i := 1; i < x[0]+1; i++ {
        add(i, i, a[i-1])
    }

    // 处理操作
    for i := 0; i < x[1]; i++ {
        var op = readArray(reader)
        add(op[0], op[1], op[2])
    }

    // 还原数组
    a[0] = b[0]
    for i := 1; i < x[0]; i++ {
        a[i] = b[i] + a[i-1]
    }
    fmt.Println(nums2string(a, " "))
}

func nums2string(x []int, sep string) string {
    var b strings.Builder
    for i := 0; i < len(x); i++ {
        b.WriteString(strconv.Itoa(x[i]))
        b.WriteString(sep)
    }
    return b.String()
}

func readLine(reader *bufio.Reader) string {
    var line, _ = reader.ReadString('\n')
    return strings.TrimRight(line, "\n")
}

func readInt(reader *bufio.Reader) int {
    var num, _ = strconv.Atoi(readLine(reader))
    return num
}

func readArray(reader *bufio.Reader) []int {
    var line = readLine(reader)
    var strList = strings.Split(line, " ")
    var nums = make([]int, 0)
    var err error
    var v int
    for i := 0; i < len(strList); i++ {
        if v, err = strconv.Atoi(strList[i]); err != nil {
            continue
        }
        nums = append(nums, v)
    }
    return nums
}

/*
输入一个长度为n的整数序列。

接下来输入m个操作,每个操作包含三个整数l, r, c,表示将序列中[l, r]之间的每个数加上c。

请你输出进行完所有操作后的序列。

输入格式
第一行包含两个整数n和m。

第二行包含n个整数,表示整数序列。

接下来m行,每行包含三个整数l,r,c,表示一个操作。

输出格式
共一行,包含n个整数,表示最终序列。

数据范围
1≤n,m≤100000,
1≤l≤r≤n,
−1000≤c≤1000,
−1000≤整数序列中元素的值≤1000
输入样例:
6 3
1 2 2 1 2 1
1 3 1
3 5 1
1 6 1
输出样例:
3 4 5 3 4 2
*/

二维差分

go

python

最后更新于

这有帮助吗?