I have a problem with a program that will tell the time. For example if you ask java what Time(4,129)is, the output should give 6 hours and 9 minutes(Because 129 minute can be simplfied.
Note: This is just a part of my code. I know my code will fail for minute values such as 120,180.
I do understand my forloop is inefficient, but that is not the problem. My problem is that my output for Time(4,129) gives me 4 hours and -51 minutes which is wrong. It should be 6 hours and 9 minutes.
How I think the code is working:
We enter the forloop, go to if statement,check if 129%60 is greater than 0 (9>0) which is true, then proceed.
2.For the body of the if statement, minutes will reduce from 129 to 69 and increment hours by 1 (It is now 5 hours). Forloop ends.
We repeat our forloop which is the 2nd iteration. Check if statement condition ,69%60>0 --> 9>0,True, go to if statement body.
minutes will change to 9 from 69 minutes and hours increment by 1. If statement ends.
Repeat if statement, Third iteration, 9%60 is false therefor if statement does not run.
Time(int x, int y) {
hours = x;
minutes = y;
for (int i = 0; i < 12; i++) {
int temp;
if (minutes % 60 > 0) {
minutes = minutes - 60;
hours = hours++;
Repeat if statement, 9%60 is false therefor if statement does not run
Is it? For minutes being 9, minutes % 60 is 9, which is greater than 0. You want minutes > 59, no modulo needed.
But even easier: hours += minutes / 60; minutes %= 60. No loop required.
It's not clear why you use a loop. But if you insist, how about
while (minutes >= 60) {
minutes -= 60;
hours += 1;
}
Your analysis for the final loop is wrong. 9 % 60 is 9. That's greater than 0 so minutes becomes -51.
This will yield the correct result, the flaw in your code is the use of modulo to figure out when the minutes should be taken into account:
class Ideone
{
public static void main (String[] args) throws java.lang.Exception
{
int x = 4;
int y = 129;
int hours = x;
int minutes = y;
for (int i = 0; i < 12; i++) {
int temp;
if (minutes > 59) {
minutes = minutes - 60;
hours = ++hours;
}
}
System.out.println("Hours: "+ hours + " minutes: " + minutes);
}
}
Related
I've made a simple code to count the occurrences of the digit '14' from a given number. I've successfully print out the counter if the given number is 10 000 000 and it took less than 1 second. When i increase the number to
10 000 000 000 it took 459 seconds. Any ideas on how to make it runs faster?
long startTime = System.nanoTime();
long counter = 0L;
for (long i = 14; i <= 10000000000L; i++)
{
String s = Long.toString(i);//i.ToString();
if (s.contains("14"))
{
counter += 1;
}
}
long endTime = System.nanoTime();
long totalTime = endTime - startTime;
long convert = TimeUnit.SECONDS.convert(totalTime, TimeUnit.NANOSECONDS);
System.out.println(convert + " seconds");
System.out.println(counter);
time taken : 459 seconds
number of 14 appears : 872348501
The most obvious optimization: don't construct strings.
Just check the last two digits of the number, and then divide by 10 until you find a 14:
boolean matches = false;
for (long num = i; num >= 14 && !matches; num /= 10) {
matches = (num % 100) == 14;
}
if (matches) {
counter += 1;
}
But, you would likely just be able to calculate the number of cases, using the inclusion/exclusion principle.
You can improve performance by combining the solution proposed by Andy Turner and java8 parallel streams:
private boolean twoDigitExist(long x, long d)
{
while (x >= d)
{
if (x % 100 == d)
return true;
x /= 10;
}
return false;
}
And the loop could be parallelized as:
long counter = LongStream.range(14, 10000000000L).parallel().filter(l->twoDigitExist(l, 14)).count();
I've been working on assignment for my homework and I'm stuck again. It's very simple task. (I think so)
For example I have 2493 seconds.
I want to convert it to this format 00:41:33
I know I could use java.utilities but simple maths could solve it too(?)
if(Time>3600) {
Hours = Time/3600;
}
if(Time<3600)
{
Hours = 0;
}
Minutes = ((Time-(3600*Hours))/60);
Seconds = ??????????;
So the only thing I don't get how do I get to know how many seconds left from this thing?
If your Time is given in seconds, you can do the following for your calculation:
int hours = Time / 3600;
int minutes = (Time % 3600) / 60;
int seconds = Time % 60;
The modulus operator gives the remainder after division, and can be used to calculate minutes and seconds.
To calculate minutes, we want to remove all time over 1 hour, so we mod Time by 3600, then we divide by 60.
To calculate seconds, because Time is already in seconds, we mod Time by 60.
Here's the general formula for convertions like this. You do have to remember to subtract the values you have previously converted. For example, after you calculate the hours, you have to subtract the hours so you can then convert the minutes.
public class TimeConverstion
{
private static void convert( int i )
{
int hours = i / 3600;
i = i - hours * 3600;
int minutes = i / 60;
i = i - minutes * 60;
int seconds = i;
System.out.printf( "Hours:%d, minutes:%d, seconds%d%n", hours, minutes,
seconds );
}
public static void main(String[] args) {
convert( 149580 );
}
}
Output of this program:
run:
Hours:41, minutes:33, seconds0
BUILD SUCCESSFUL (total time: 0 seconds)
Have a start time and end time that has to be split into equal interval.
E.g.
Start Time: 10AM,
End Time: 14PM,
Split Time: 30 minutes
The output has to be something like this -
::::Output :::
[{time:"10:00"},{time:"10:30"},{time:"11:00"},{time:"11:30"},{time:"12:00"},{time:"12:30"},{time:"13:00"},{time:"13:30"},{time:"14:00"}]
Thanks everyone in advance.
First, convert hours to minutes.
10AM = 10 * 60 minutes
2PM or 14h = 14 * 60 minutes
Then, in order to convert minutes back to hours :
minutes / 60 gives the number of hours
minutes % 60 gives the number of the minutes in the last hour.
If you want to display hours/minutes always on 2 digits, and eventually pad with a leading zero, use :
String result = String.format("%02d", minutes/60);
(2 indicates that you want 2 digits and 0 indicates that you pad with zeros)
That said, there are 2 ways of going from 10*60 to 14*60 with steps of 30 minutes :
The most intuitive : the while loop
public static void interval(int begin, int end, int interval) {
int time = begin;
while (time <= end) {
System.out.println(String.format("%02d:%02d", time / 60, time % 60));
time += interval;
}
}
But I don't like while loops. If you do it wrong (or if the input data are wrong), it ends in infinite loops.
The other way : as you know the begin, the end and the step, use a for loop :
public static void interval2(int begin, int end, int interval) {
for (int time = begin; time <= end; time += interval) {
System.out.println(String.format("%02d:%02d", time / 60, time % 60));
}
}
Test :
interval2(10 * 60, 14 * 60, 30);
Result :
10:00
10:30
11:00
11:30
12:00
12:30
13:00
13:30
14:00
Part of an assignment I have for a beginning Java class is to take a time entered in as a string and convert it (while rounding to the nearest quarter hour) to a double and store it in an array. The part I am having difficult with is what to do with the two integers I receive from the split method of the String class. How do I make the two integers into one double to use in the array? (So it would be like hours.minutes, or 5.25)
Here is a snippet of code from a program I am working on:
public static double convertClockOutTimes(String clockOut){
double convertedTimeOut = 0;
String time = clockOut;
int hours;
int minutes;
String[]splitFields;
splitFields = time.split(":");
hours = Integer.parseInt(splitFields[0]);
minutes = Integer.parseInt(splitFields[1]);
if (minutes <= 7)
{
minutes = 0;
}
else if (minutes >= 8 || minutes <= 22)
{
minutes = 15;
}
else if (minutes >= 23 || minutes <= 37)
{
minutes = 30;
}
else if (minutes >= 31 || minutes <= 53)
{
minutes = 45;
}
else
minutes = 0;
hours = hours + 1;
convertedTimeOut = //This is where I don't know what to do!!
return convertedTimeOut;
}
I think the trick is to use a bit of math here. You could always do the following:
double convertedTimeOut = Math.round(minutes / 15.0) * 0.25 + hours;
then you don't need the if-else tree to figure out the nearest quarter hour.
There are 15 minutes in a quarter hour, and a quarter hour is 0.25 hours. Using the formula above, you are dividing the minutes into how many quarters of an hour you've got (0-4), which you then multiply by how many hours are in a quarter hour. Then add that to the hours you've got.
Math.round just does the rounding for you.
I'm guessing what's giving you the most trouble is how to deal with the minutes. Try this:
double minutesAsDecimal = 0.01 * minutes;
So if the number of minutes was 24, you would end up with 0.24. I bet you'll know where to go from there.
Just as a side note, your if and else ifs are not doing what you think they are. But since it's homework.. Just take a closer look at your logic there.
Your conditions should be AND not OR:
if(minutes >= 8 && minutes <= 22)
Etc, or better yet, a single statement, simply
minutes = ((minutes + 7) % 15) * 15;
which calculates the rounding using arithmetic rather than logic.
I am developing a Java countdown timer. I am totally new to Java though have done some C++ before so it's not all totally new. I am having problems with this - can anyone easily see what I have done wrong in the logic?
What is happening:
On run, if you enter in for example 23 in hours leave mins blank and put in 5 secs - the 5 secs should count to 0 - the mins should go to 59 and the hours to 22. However once the 5 secs elapses all digits go to zero.
If on the input box I enter though 23 hours 1 in minutes and 5 in secs - when the 5 has elapsed it changes to 22 hours 59 mins 59 secs so I know its nearly there (just hoping I may have missed something silly.
Finally the last problem with the logic - if I for example enter 30 mins 5 secs when the 5 have elapsed the mins go to 29 the secs go to 59 and continue counting down but the hours go to -1. Code below - sorry for long post but wanted to paint the scenarios - Thanks - Colly
Integer sec = new Integer (seconds.getText ());
Integer min = new Integer (minutes.getText ());
Integer hr = new Integer (hours.getText ());
int temp1 = sec.intValue ();
int temp2 = min.intValue ();
int temp3 = hr.intValue();
temp1--;
if (temp1 == -1 )
{
temp1 = 59;
temp2--;
if (temp2 == 0 && temp3 != 0)
{
temp2 = 59;
}
temp3--;
}
hr = new Integer (temp3);
sec = new Integer (temp1);
min = new Integer (temp2);
hours.setText (hr.toString ());
minutes.setText (min.toString ());
seconds.setText (sec.toString ());
if (seconds.getText ().length () == 1)
seconds.setText ("0" + seconds.getText ());
Please don't do time counting manually, it is painful to write and painful to read. I don't even mention how it feels to debug it.
The Calendar class may be interesting:
Calendar c = Calendar.getInstance();
c.clear(); // To reset all fields
c.set(Calendar.HOUR_OF_DAY, 23);
c.set(Calendar.MINUTE, 0);
c.set(Calendar.SECOND, 5);
c.add(Calendar.SECOND, -1);
And you don't have to worry about counting.
Using Calendar for date/time is (despite its shortcomings) the right thing. There's a simple alternative here: Compute the total seconds like
int total = 3600 * hrs + 60 * min + sec;
decrement and decompose using
int x = total;
hrs = x / 3600;
x = x - 3600 * hrs;
min = x / 60;
x = x - 60 * min;
sec = x;
This is surely less error-prone than working on the parts, especially for more complicated operations. But again, I recommend using Calendar.
May it's because you are leaving the minutes text box blank. Can you try with a 0 there?
On run, if you enter in for example 23 in hours leave mins blank and
put in 5 secs - the 5 secs should count to 0 - the mins should go to
59 and the hours to 22. However once the 5 secs elapses all digits go
to zero.
I renamed your vars:
s--;
if (s == -1 )
{
s = 59;
m--;
if (m == 0 && h != 0)
{
m = 59;
}
h--;
}
If the seconds are 0, you decrement minutes. Then you test something, but without further tests, you always decrement hours.
While the code doesn't do what it should, it doesn't do what you describe. Is this your real code?