Valid Triangle Number

update Aug 2,2017 22:36

LeetCodearrow-up-right

Given an array consists of non-negative integers, your task is to count the number of triplets chosen from the array that can make triangles if we take them as side lengths of a triangle.

Example 1:

Input: [2,2,3,4]
Output: 3
Explanation:
Valid combinations are: 
2,3,4 (using the first 2)
2,3,4 (using the second 2)
2,2,3

Note:

The length of the given array won't exceed 1000. The integers in the given array are in the range of [0, 1000].

Basic Idea:

这里arrow-up-right有一个双指针解法的说明.

三种思路,大致说一下:

  1. 首先想到的是暴力枚举三条边然后判断是否valid,用combination的dfs算法,时间复杂度是(C(n,3)),O(n^3),结果TLE了;

  2. 接下来想到我们可以先排序原数组,固定两条边a,b,计算出第三条边的范围(a + b > c),然后用binary search找,找到之后target和b之间的点都可以构成第三边。枚举所有两边的组合耗时O(n^2),bi search每次耗时O(logN),总的 time complexity 是 O(n^2 * log(n))。AC了;

  3. 接下来我们想到可以先排序,然后固定第三边 c 从最右端往左移。对每个 c,使用双指针找与之相配的a, b的范围(a 从最左端向右,b 从 c-1 向左,如果满足 a+b>c 则将 a,b 之间点的个数加入结果,作为 a 的可能值,然后 b--。如果不满足 a+b>c ,则令 a 右移一位,继续判断。到 a >= b 结束,c--,进行下一波判断)。

    Nov 30,2017 补充解释

    这种方法相当于先对于每个C,对于每个B,找A的范围。时间复杂度因该是对于每个C需要O(n)的时间,总共为 O(n^2);

Python Code:

Java Code:

update Nov 29, 2017

Update

首先需要明确一个前提,两短边之和大于第三边是一定可以构成一个三角形的;

Binary search Java solution