CodeChef is a non-commercial competitive programming community
Login
Username (New User? Signup) Password (Forgot Password?)
Signup
Login or
Signup with
Connect
Note
  • Publicize your achievements on your Facebook Wall.
  • Challenge your friends or ask them for help.

Site Navigation

  • PRACTICE
    • Easy
    • Medium
    • Hard
    • Challenge
    • Peer
  • COMPETE
    • All Contests
    • June Long 2012
    • May Cook-Off
    • May Long 2012
  • DISCUSS
    • Forums
    • Blog
    • Wiki
    • Facebook
    • Twitter
  • COMMUNITY
    • CodeChef Meetups
    • Campus Chapters
    • Host your Contest
    • User Groups
    • CodeChef TechTalks
    • All Educational Initiatives
  • HELP
    • Frequently Asked Questions
    • FAQ for problem setters
    • Problem Setting
    • Tutorials
    • Long Contest Ranks
    • Short Contest Ranks
    • Event Calendar
  • ABOUT
    • About CodeChef
    • Team CodeChef
    • Press Room
    • CodeChef Financials
    • CodeChef Sponsorships
    • CEO's Corner
    • Contact Us
    • About Directi
Home » Wiki » Tutorial for Not a Triangle

Tutorial for Not a Triangle

 

The problem Not a Triangle asks us to find out the number of triplets from the given list that do not form a triangle. Let us revise a fundamental property - "Three numbers cannot form a triangle if the sum of any two is less than the third". Keeping this in mind, we can start building our solution.

Let us take a look at a naive solution. Consider all possible triplets and for each triplet check if the numbers are such that they do not form a triangle. Such a solution would work, but will it run within the time limit? Let us take a look at the time complexity of such a solution. It is of the order O(n^3). The value of 'n' can go up to 2000. So we are looking at more than 10^9 operations. This will not work in the given time period. So, we need to reduce the time complexity of our solution.

One thing we need to observe is that we don't need the actual triplets, we just need the number of triplets. In the solution described above, given 2 numbers, we need roughly 'n' comparisons in the worst case to find the number of values for which, having fixed the other two values, the sum of the two values selected is lesser than the third value we select. Now, if we are able to find such a value X for the selected 2 values such that X > sum_of_the_two_values, then any value greater than or equal to X will also satisfy the equation. So, our problem boils down to finding the lowest value X such that having selected 2 of the numbers, X > sum_of_the_two_values.

In such cases, sorting the values initially can help us. Let us sort the numbers that we take in for each test case. Now, having selected 2 of the numbers, we need to be able to find the number X in a complexity lower than O(n). As we can see, this is possible by using a technique called binary search. Consider that our array(A) of elements in sorted order is {10,20,30,40,50} and the 2 elements we have selected are 10 and 20. Now, we need to find the lowest number X such that X > 10+20. For this, we consider the interval of elements immediately after 20 till the end. In binary search, we make use of the fact that if a number T does not satisfy the given criteria, then either the numbers before T or the ones after T too will not satisfy the criteria. The technique is called binary search as at every stage, we maintain two values 'low' and 'high' which represent the interval that we are searching. We find the midpoint of this interval 'mid'=(low+high)/2. If the value at position 'mid' satisfies our criteria i.e. A[mid]>10+20, then there can be a lower value that satisfies the same criteria in the interval [low,mid]. So, we make the current value of 'mid' as the new value of 'high' and carry out the same procedure in the new interval. If we find that the new value at position 'mid' does not satisfy the criteria, then we can safely disregard all values below that value including it. This gives us our new interval as [mid+1,high]. Eventually, we will reach a state where the values of 'low' and 'high' are the same. This is when we have either found our required value X i.e. the lowest value such that X>sum_of_other_two_values or such a value does not exist in the array that we have.

Considering our array, let us see the values of low and high at every iteration. We start off with low=3 and high=5 which are the positions immediately after 20 and the last position respectively.

Iteration Low High Mid A(mid)
1 3 5 4 40

Now, we see that A[Mid] is 40 which is greater than 10+20. In the worst case, our answer can be 40, though there might be a chance that a better answer below 40 might be found. So, we change our interval to (Low, Mid), which is the same as changing the value of High to that of Mid. So in the second iteration, our values are:

Iteration Low High Mid A(mid)
2 3 4 3 30




We carry out integer division so (3+4)/2 = 3. Now 30 is not greater than 10+20. Thus, we can rest assured that we can't find the required number in the interval Low to Mid inclusive. So we need to search for an answer in the interval (Mid+1, High) which is the same as changing the value of Low to that of Mid+1. So in the next iteration our values change to :

Iteration Low High Mid A(mid)
3 4 4 4 40



We see that the values of Low and High are equal. So we have either found the required value X or such a value does not exist. We break out of the loop and make a final check to see if A[Mid] is greater than 10+20 and we see that it is. So, all numbers greater than and including the value at position Mid will not form a triangle with our selected numbers 10 and 20. This number is '2' and the numbers are 40 and 50. We add this to our final answer and continue finding other triplets.

Some care needs to be taken so that we don't consider the same triplet more than once. For this, selection of the two numbers needs to be done in such a way that the position of the second number being selected is always greater than the position of the first number. Also, the position of the third number is greater than that of the second number.

With a bit of preprocessing and usage of extra memory, it is possible to find the answer with a lower time complexity. We leave that as an exercise for the reader.

 

 


Comments

  • Login or Register to post a comment.

I codded this problem with

magiix @ 11 Feb 2010 05:26 AM

I codded this problem with binary search and bubble sort and still for an input of 2000 sticks it gets the answer after 18 secs .

I'm not sure why you're using

triplem @ 11 Feb 2010 05:49 AM

I'm not sure why you're using bubble sort which is a slow sort, but even still, you must have coded something wrong to get that sort of time.

how can i get the running tym

anu_kc @ 30 Mar 2010 04:56 PM

how can i get the running tym of my code as karim is getting 18 secs...how can i know this??

i solved the problem

shreydutta.28 @ 6 Apr 2010 02:31 AM

i solved the problem accordingly and getting the right answer but for some test cases which i don't know, answers are wrong........

my selection of two numbers("first" and "second") are like this.....................

at the start first is pointing to the first element and second to the second........and third can be between third to the last element....as said in the tutorial.......

if i get a minimum 'X'.... such that X > first+second;

then my second selection of numbers will be first remains the but second is pointing to third and third can be between fourth and the last.....again if i get a minimum X > first + second... i repeat the same procedure.......n if any time i din get the minmum required 'X' then i check if second - first <= 2..... if so then i abort finding more......or else i do first = intial second(i.e. second pointing to the second)......second = to the very next element of first......... then i repeat the same procedure......... i m posting that part of my code.... plz take a look.....  n if possible provide me with some test case which wont work with that........................

 

int x = 0, y = 1,z = y; bool flag = true;
while(flag){                                  
int a= stick[x],b = stick[z];
int low = z+1, high = n-1,mid = (low+high)>>1;

while(low<n&&high<n&&low!=high){
if(stick[mid]>a+b) high = mid,mid = (low+high)>>1;
else  low = mid+1, mid = (low+high)>>1;
}
if(stick[mid]>a+b)count += (n-mid),z++;
else if(z-x<=2)flag =0;
else x = y++,z=y;
}

any one?

shreydutta.28 @ 6 Apr 2010 09:59 PM

any one?

CodeChef is a non-commercial competitive programming community
  • About CodeChef
  • About Directi
  • CEO's Corner
  • C-Programming
  • Programming Languages
  • Contact Us
© 2009 Directi Group. All Rights Reserved. CodeChef uses SPOJ © by Sphere Research Labs
In order to report copyright violations of any kind, send in an email to copyright@codechef.com
CodeChef a product of Directi
The time now is:
CodeChef - A Platform for Aspiring Programmers

CodeChef was created as a platform to help programmers make it big in the world of algorithms, computer programming and programming contests. At CodeChef we work hard to revive the geek in you by hosting a programming contest at the start of the month and another smaller programming challenge in the middle of the month. We also aim to have training sessions and discussions related to algorithms, binary search, technicalities like array size and the likes. Apart from providing a platform for programming competitions, CodeChef also has various algorithm tutorials and forum discussions to help those who are new to the world of computer programming.

Practice Section - A Place to hone your 'Computer Programming Skills'

Try your hand at one of our many practice problems and submit your solution in a language of your choice. Our programming contest judge accepts solutions in over 35+ programming languages. Preparing for coding contests were never this much fun! Receive points, and move up through the CodeChef ranks. Use our practice section to better prepare yourself for the multiple programming challenges that take place through-out the month on CodeChef.

Compete - Monthly Programming Contests and Cook-offs

Here is where you can show off your computer programming skills. Take part in our 10 day long monthly coding contest and the shorter format Cook-off coding contest. Put yourself up for recognition and win great prizes. Our programming contests have prizes worth up to Rs.20,000 and $700lots more CodeChef goodies up for grabs.

Discuss

Are you new to computer programming? Do you need help with algorithms? Then be a part of CodeChef's Forums and interact with all our programmers - they love helping out other programmers and sharing their ideas. Have discussions around binary search, array size, branch-and-bound, Dijkstra's algorithm, Encryption algorithm and more by visiting the CodeChef Forums and Wiki section.

CodeChef Community

As part of our Educational initiative, we give institutes the opportunity to associate with CodeChef in the form of Campus Chapters. Hosting online programming competitions is not the only feature on CodeChef. You can also host a coding contest for your institute on CodeChef, organize an algorithm event and be a guest author on our blog.

Go For Gold

The Go for Gold Initiative was launched about a year after CodeChef was incepted, to help prepare Indian students for the ACM ICPC World Finals competition. In the run up to the ACM ICPC competition, the Go for Gold initiative uses CodeChef as a platform to train students for the ACM ICPC competition via multiple warm up contests. As an added incentive the Go for Gold initiative is also offering over Rs.8 lacs to the Indian team that beats the 29th position at the ACM ICPC world finals. Find out more about the Go for Gold and the ACM ICPC competition here.

Domain Name Registration, Web hosting, and Website Design provided by BigRock.com