1109. 航班预订统计

法一:暴力

class Solution {
    public int[] corpFlightBookings(int[][] bookings, int n) {
        int[] res = new int[n];
        for (int i = 0; i < bookings.length; i++) {
			int begin = bookings[i][0];
			int end = bookings[i][1];
			int num = bookings[i][2];
			for (int j = begin-1; j < end; j++) {
				res[j] += num;
 			}
		}
        return res;
    }
}

时间复杂度O(bookings.length*j),应该超时的,不知道为什么还过了。

空间复杂度O(n)

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-thEZds3q-1580281930050)(C:\Users\hp\AppData\Roaming\Typora\typora-user-images\image-20200129095524428.png)]

法二:差分数组

设a[i]表示第i个航班预订的座位数。

定义一个差分数组tag[],tag[i]表示第i个航班与第i-1个航班预订座位的差,即tag[i] = res[i] - res[i - 1]。

这样每次扫描到[i, j, k],就不需要对区间中的每一个数进行修改操作了,只需要将tag[i]增加k,tag[j + 1]减少k即可,因为区间中的每一个航班都增加相同的座位,它们之间的差并未改变。

本题要求返回每一个航班座位数,所以最后要计算数组res
r e s [ i ] = r e s [ i 1 ] + t a g [ i ] res[i] = res[i - 1] + tag[i]

class Solution {
    public int[] corpFlightBookings(int[][] bookings, int n) {
        int[] res = new int[n];
        int[] tag = new int[n+2];
        for (int i = 0; i < bookings.length; i++) {
			int begin = bookings[i][0];
			int end = bookings[i][1] + 1;
			int num = bookings[i][2];
			tag[begin]  += num;
			tag[end]  -= num;
		}
        res[0] = tag[1];
        for (int i = 1; i < n; i++) {
			res[i] = res[i-1] + tag[i+1];	//下标从0开始,tag+1,不理解打一下表就懂了
		}
        return res;
    }
}

时间复杂度:O(max(n, bookings.length))

空间复杂度:O(n)

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-NNe7yNW8-1580281930053)(C:\Users\hp\AppData\Roaming\Typora\typora-user-images\image-20200129102819835.png)]

法三:树状数组

class Solution {
	public int lowbit(int x) {
		return x&(-x);
	}
    public int[] corpFlightBookings(int[][] bookings, int n) {
    	int[] res = new int[n+1];
    	for (int[] a : bookings) {
			update(a[1],a[2], res);
			update(a[0]-1, -a[2], res);
		}
        for (int i = 1; i <= n; ++i) {
            res[i-1] = getSum(i, n, res);
        }
        int[] newres = new int[n];
        for (int i = 0; i < n; i++) {
			newres[i] = res[i];
		}
        return res;
    }

    // a[1..x] 都加 v
    // O(logn)
    public void update(int x, int v, int[] res) {
        for (int i = x; i > 0; i -= lowbit(i)) {
            res[i] += v;
        }
    }
    
    // O(logn)
    int getSum(int x, int n, int[] res) {
        int sum = 0;
        for (int i = x; i <= n; i += lowbit(i)) {
            sum += res[i];
        }
        return sum;
    }
};

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-KDDhuMBT-1580281930053)(C:\Users\hp\AppData\Roaming\Typora\typora-user-images\image-20200129122732435.png)]

时间复杂度:O(nlogn)

就这个题来说,效率不算高,只是一种解题思路。

发布了56 篇原创文章 · 获赞 4 · 访问量 1706

猜你喜欢

转载自blog.csdn.net/qq_41342326/article/details/104107127