[Codility] CountTriangles

A zero-indexed array A consisting of N integers is given. A triplet (P, Q, R) is triangular if it is possible to build a triangle with sides of lengths A[P], A[Q] and A[R]. In other words, triplet (P, Q, R) is triangular if 0 ≤ P < Q < R < N and:

  • A[P] + A[Q] > A[R],
  • A[Q] + A[R] > A[P],
  • A[R] + A[P] > A[Q].

For example, consider array A such that:

  A[0] = 10    A[1] = 2    A[2] = 5
  A[3] = 1     A[4] = 8    A[5] = 12

There are four triangular triplets that can be constructed from elements of this array, namely (0, 2, 4), (0, 2, 5), (0, 4, 5), and (2, 4, 5).

Write a function:

int solution(vector<int> &A);

that, given a zero-indexed array A consisting of N integers, returns the number of triangular triplets in this array.

For example, given array A such that:

  A[0] = 10    A[1] = 2    A[2] = 5
  A[3] = 1     A[4] = 8    A[5] = 12

the function should return 4, as explained above.

Assume that:

  • N is an integer within the range [0..1,000];
  • each element of array A is an integer within the range [1..1,000,000,000].

Complexity:

  • expected worst-case time complexity is O(N2);
  • expected worst-case space complexity is O(N), beyond input storage (not counting the storage required for input arguments).

给定正整数数组A,长度为N,下标从0开始,求(P,Q,R),满足0<=P<Q<R<N 并且 A[P] + A[Q] > A[R], A[Q] + A[R] > A[P], A[P] + A[R] > A[Q]的三元组个数。

数据范围 N [0..1000], 数组元素[1..10^9]。

要求复杂度 时间O(N ^ 2) ,空间 O(1)。

分析: 显然我们不能枚举……我们可以把数组排序 O(NlogN),甚至O(N^2)的排序都可以。然后还是枚举,只不过枚举两条较小的边A[x] , A[y], 然后我们考虑最大边A[z],设想假设我们固定x, 当y变大时A[x] + A[y]也变大,我们需要A[x] + A[y] > A[z], y变大之前的那些z值现在依然也满足条件,所以我们只要接着上次满足条件的最大的z,继续循环就可以了。所以对于同一个x来说,y和z的变化都是O(N)的。总复杂度O(N^2)。

 1 // you can use includes, for example:
 2 #include <algorithm>
 3 
 4 // you can write to stdout for debugging purposes, e.g.
 5 // cout << "this is a debug message" << endl;
 6 
 7 int solution(vector<int> &A) {
 8     // write your code in C++11
 9     sort(A.begin(), A.end());
10     int a, b, c;
11     int res = 0;
12     for (a = 0; a < (int)A.size() - 2; ++a) {
13         c = a + 2;
14         for (b = a + 1; b < (int)A.size() - 1; ++b) {
15             for (c = max(c, b + 1); c < A.size() && A[a] + A[b] > A[c]; ++c);
16             res += c - b - 1;
17         }
18     }
19     return res;
20 }

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值