What's the time?

25

2

I like to save time quite literally, by wearing three watches on my wrist... Problem is they each give a different time. One watch is x minutes behind the actual time. One watch is x minutes ahead of the actual time. The last watch shows the actual time.

Problem is, I can't tell which watch has the correct time...

From the time displayed on each watch, determine the actual time. If it is not possible to determine the time, print "Look at the sun".

Input: Three readings, separated by single space characters: H1:M1 H2:M2 H3:M3 In each reading H1,H2,H3 represent the hours displayed (0 < H1,H2,H3 < 13), and M1,M2,M3 represent the minutes displayed (0 <= M1,M2,M3 < 60). If the number of minutes is less than 10, a leading 0 is prepended in the input. Similarly, is the number of hours is less than 10, a leading 0 is prepended in the input.

Output: The correct time is HH:MM where HH:MM is the correct time. If no correct time can be determined, it displays Look at the sun.

Input 1: 05:00 12:00 10:00

Output 1: The correct time is 05:00

Input 2: 11:59 12:30 01:01

Output 2: The correct time is 12:30

Input 3: 12:00 04:00 08:00

Output 3: Look at the sun

Shortest code wins... No special penalties apply. Also, bear in mind that we're dealing with a 12-hour clock... I don't care about AM or PM... Imagine we're dealing with analogue watches...

WallyWest

Posted 2015-06-03T06:11:12.187

Reputation: 6 949

By correct time, you mean the current local time ? – Optimizer – 2015-06-03T06:21:05.840

@Optimizer One of the watches will contain the correct time, the other two will be X minutes plus/minus from the correct time... I've mentioned that in the brief... – WallyWest – 2015-06-03T06:27:47.387

@Dennis Output 3 clearly shows a response of Look at the sun, so yes... – WallyWest – 2015-06-03T07:09:18.110

Why is Output 3 look at the sun? Would 8:00 not be correct, and why not? – Sanchises – 2015-06-03T07:27:24.540

7@sanchises Because they're 4 hours apart. 12:00 is exactly between 8:00 and 4:00 too, you know... – Siguza – 2015-06-03T07:40:45.273

@Siguza I knew I was missing something obvious! – Sanchises – 2015-06-03T12:32:52.770

1You say the output is of the form The correct time is HH:MM, without a full stop, but then proceed to include a full stop in the first two examples. Which version is correct? – Sp3000 – 2015-06-03T15:49:39.420

Also additional test case: 07:21 08:39 08:00 – Sp3000 – 2015-06-03T16:03:10.817

1Is it allowed to to read the times as command line arguments? – Dennis – 2015-06-03T16:38:56.637

1As in whattimeisit 07:21 08:39 08:00 ? Sure! – WallyWest – 2015-06-03T23:43:15.177

@Sp3000 Valid point, I've corrected the output format... – WallyWest – 2015-06-03T23:45:05.370

Answers

10

CJam, 86 83 77 75 71 bytes

"The correct time is "ea{aea+':f/60fb(f-:+720%!},{];"Look at the sun"}*

Thanks to @jimmy23013 for golfing off 6 bytes from my code.

Try it online in the CJam interpreter.

Test cases

$ cjam time.cjam 05:00 12:00 10:00; echo
The correct time is 05:00
$ cjam time.cjam 11:59 12:30 01:01; echo
The correct time is 12:30
$ cjam time.cjam 12:00 04:00 08:00; echo
Look at the sun

How it works

"The correct time is "
        e# Push that string.
ea      e# Push the array of command-line arguments.
{       e# Filter; for each time T:
  a     e#   Wrap T in an array.
  ea+   e#   Concatenate with the array of all times.
  ':f/  e#   Split each time at the colon.
  60fb  e#   Consider it a base 60 integer.
  (f-   e#   Shift out the converted T and subtract it from the remaining times.
  :+    e#   Add them.
  720%! e#   Push 1 is the sum is 0 modulo 720 and 0 if not.
},      e#   Keep the time iff a 1 has been pushed.

        e# The array on the stack now contains one or three times.

{       e# Reduce; for each time but the first:
  ];    e#   Discard the entire stack.
  "Look at the sun"
        e#   Push that string.
}*      e#

Dennis

Posted 2015-06-03T06:11:12.187

Reputation: 196 637

1qS/_':f/60fb_f{f-:+720%!,}\"The correct time is "f\2/.e&$("Look at the sun"@?. b implies :i. – jimmy23013 – 2015-06-03T07:17:12.557

3"The correct time is "lS/_':f/60fb:T.{Tf-:+720%{}@?}{];"Look at the sun"}*. – jimmy23013 – 2015-06-03T08:13:13.993

You missed the case when x=0 – Lakshay Garg – 2015-06-03T19:57:14.087

@LakshayGarg: The question says that they each give a different time. That would be false if x = 0. – Dennis – 2015-06-03T20:07:23.723

@Dennis You may be able to reduce it further, the full stop at the end isn't required... – WallyWest – 2015-06-03T23:46:25.133

@WallyWest: 4 whole bytes! Thanks for notifying me. – Dennis – 2015-06-03T23:52:08.490

@Dennis NP, oh, and did you see my response about input being accepted as command line arguments? – WallyWest – 2015-06-03T23:54:02.680

I might be missing something in the question, either explicit or implicit, that would prevent this from being a problem, but if I enter "05:00 12:00 11:00", I get an IndexOutOfBoundsException. – IronFlare – 2015-06-04T00:17:04.823

@IronFlare: The three times have to be equally spaced. One watch is x minutes behind the actual time. One watch is x minutes ahead of the actual time. – Dennis – 2015-06-04T00:46:18.670

@WallyWest: Yes, my latest revision is taking advantage of that. – Dennis – 2015-06-04T00:47:04.727

@Dennis And there it is-- the part of the question I was missing. Thanks :) – IronFlare – 2015-06-04T01:38:05.847

7

JavaScript (ES6), 164 168 172

For each reading, calc the distance from the other two. The one that have the same distance is what you need. If there is more than one, then you can't tell.

F=s=>(s=s.split(' '))
  .map(x=>([h,m]=x.split(':'),+m+(h%12)*60))
  .map((v,i,z)=>(v+v-z[++i%3]-z[++i%3])%720||'The correct time is '+s[k+=i],k=-2)
[k]||'Look at the sun'


// TEST

out=x=>O.innerHTML += x+'\n';

['12:30 01:01 11:59', '11:50 11:55 12:00', '05:00 12:00 10:00', '12:10 04:10 08:10', '07:00 06:00 08:00']
.forEach(x => out(x + ' -> ' + F(x)))

go=_=>out(I.value + ' -> ' + F(I.value))
<pre id=O></pre>
<input id=I><button onclick="go()">Test</button>

edc65

Posted 2015-06-03T06:11:12.187

Reputation: 31 086

Should it not give 3:00 for the input 3:00 3:00 3:00. When x=0 :P – Lakshay Garg – 2015-06-03T19:53:53.810

4@LakshayGarg no. Problem is they each give a different time so x cannot be 0. – edc65 – 2015-06-03T20:11:49.370

With each upvote you get, you should edc65++. – Alex A. – 2015-06-04T18:28:39.527

4

Python 3, 166 163 bytes

L=input().split()
f=lambda x:int(x[:2])*60+int(x[3:])
s=""
for a in L:s=[s,s and"Look at the sun"or"The correct time is "+a][(sum(map(f,L))-3*f(a))%720<1]
print(s)

Uses

      a-b == b-c
<==>  a+c-2*b == 0
<==>  (a+b+c)-3*b == 0

with arithmetic being minutes modulo 720.

Sp3000

Posted 2015-06-03T06:11:12.187

Reputation: 58 729

Using a similar approach (a+a-b-c==0) I found that sorting is not needed. Did you try to avoid it? – edc65 – 2015-06-03T17:07:08.353

@edc65 I did try to keep a count instead but I think it turned out longer. I also had a+a-b-c initially but that's a lot of calls to f (and pre-list-comp is long) – Sp3000 – 2015-06-03T17:13:17.533

2

Python 2, 254 ... 199 207 203 194 200 Bytes

Probably a few ways to shorten this, give me some time..

t=[x.split(':')for x in raw_input().split()]
a,b,c=[int(x[0])*60+int(x[1])for x in t]
print["The correct time is "+':'.join(t[[(c+a)%720%(b/2)<1,2][(a+b)%720%(c/2)<1]]),"Look at the sun"][(a-b)%240<1]

Thanks to Sp3000 helping me fix this.

Kade

Posted 2015-06-03T06:11:12.187

Reputation: 7 463