Checking which date comes first? - java

It seems logical that there should be some simple method to check which DatePicker object comes first but I can't find done.
// so if you had two objects
final DatePicker start_datepicker = (DatePicker)findViewById(R.id.DatePickerStart);
final DatePicker end_datepicker = (DatePicker)findViewById(R.id.DatePickerEnd);
// I was thinking something along the lines of:
if (end_datepicker > start_datepicker) {
// something
}
// or is there something like
if (end_datepicker.isLarger(start_datepicker)) {
// Something
}
Is this possible or does anyone know of something simple along these lines to compare to dates?

A DatePicker is a UI widget for displaying a date. You don't set it by assignment (as in your code) but by calling it's init method. Typically you would then track the date using an OnDateChangedListener. Nevertheless, you can compare the current dates displayed on two such widgets with something like this:
/** Returns a number <0, 0, or >0 when dp1 displays a date <, =, or > dp2. */
public int compare(DatePicker dp1, DatePicker dp2) {
int compare = dp1.getYear() - dp2.getYear();
if (compare == 0) {
compare = dp1.getMonth() - dp2.getMonth();
if (compare == 0) {
compare = dp1.getDay() - dp2.getDay();
}
}
return compare;
}

You should take the resulting values from the date pickers and convert them to Date objects which will then allow you to easily compare the values rather than going the route of writing your own Comparator that relies on the UI component.

I actually wrote a Java class specifically to handle this situation for Android. Feel free to use it and include it in your app! It's documented, as well.

Date has before() and after() methods.. just for that.

Related

Limit uses of a function in a period of time (android)

I want to limit the calls to a function within one day.
The problem is I'm a bit confused of how to use the Date and Calendar classes...
private int usesLeft //Set every day to the number of uses
private void function() {
if(usesLeft > 0) {
//Function's body...
}
usesLeft--;
}
I need to find out when a new day starts in order to reset the usesLeft variable.
Well I found a solution...
The better side of this solution is that the user can't "cheat" because then he'll lose activity days (If my analysis of the code behavior is right).
if(lastDayActive < (int)Math.floor(System.currentTimeMillis()/86400000)) {
usesLeft = 100;
//Initializes the day value
lastDayActive = (int)Math.floor(System.currentTimeMillis()/86400000);
}
If there's any way to prevent the user from manually changing the date and therefore gaining more uses I'd really like to hear about it.

How to properly compare two Float wrappers in Java?

I already know how to compare floats and this is not the question.
When I compare float I cannot just do that:
if(flot1 == flot2) {
// do something
}
Indeed I was always taught to do something like this:
if(Math.abs(float1 - float2) < epsilon) {
// do something
}
But the question is when I use float wrappers... for example there is something as simple as the method equal():
if(floatWrapper1.equals(floatWrapper2)) {
// do something
}
But reading the documentation that this is equivalent to:
if(floatWrapper1.floatValue() == floatWrapper2.floatValue()) {
// do something
}
That is the same like the example (2) that is wrong for the purpose of comparison.
Looking in internet I then found some examples like this:
if(Float.compare(flotWrapper1, floatWrapper2) == 0) {
// do something
}
But, I was wonder if this is right neither. How should I then compare two float wrappers?
The simple answer is because of Auto boxing, comparing Floats is no different than comparing floats. Save for a null pointer check, you can treat them equivalently.

JFreeChart TimeSeries array exception

this is my first question here ever, and I would appreciate if you can help me.
Since the code I have is way too large to post here, I'll try to describe what my problem is in short.
So, I have made TimeSeries array within my class and array list from where I get values for time series:
private TimeSeries[] seriesArray = new TimeSeries[10];
ArrayList<TempClass> valuesFromArrayList = new ArrayList<>();
I need to make TimeSeries array, because I want to be able to show multiple timeseries graphs. Using only one TimeSeries and addOrUpdate method isn't what I want because then values get mixed when I create more graphs. So, I add values like this:
for(int i = 0; i < valuesFromArrayList.size(); i++)
{
TempClass obj = (TempClass) valuesFromArrayList.get(i);
int timeStamp = obj.getTimeStamp();
int hrsDiff;
int minsDiff;
int secsDiff;
hrsDiff = timeStamp / 3600;
timeStamp = timeStamp - hrsDiff * 3600;
minsDiff = timeStamp / 60;
timeStamp = timeStamp - minsDiff * 60;
secsDiff = timeStamp;
seriesArray[Integer.parseInt(comboBoxValue) - 1].add(new Second(secsDiff, minsDiff, hrsDiff, day, month, year), Math.abs(obj.getValue()));
}
What this part of code does is that it reads values and timestamps from ArrayList I created. There is comboBox where user can choose which timeSeries array index will be in graph. So, if user chooses value 9 from comboBox, timeSeries from index 8 will be chosen and plotted on graph. TimeStamp is simply number of seconds that passed since 00:00:00 at day when values were taken.
TempClass is defined as:
class TempClass
{
private int timeStamp;
private double value;
public TempClass(int a, double b)
{
timeStamp = a;
value = b;
}
public int getTimeStamp()
{
return timeStamp;
}
public double getValue()
{
return value;
}
public void setValue(double val)
{
value = val;
}
}
The problem I have is that when I try to make second (2nd) graph, that is another index of TimeSeries array, I get message:
You are attempting to add an observation for the time period Thu Apr 30 00:00:00 CEST 2015 but the series already contains an observation for that time period. Duplicates are not permitted. Try using the addOrUpdate() method.
I don't want to use addOrUpdate method, I need add method. Values in ArrayList I use to put values into timeSeries are fine, I am 300% sure. I already checked input from comboBox value and it gives correct values.
I have no explanation other that for some reason, even if array index is changed, data I want to write into the series goes to the old series (that is, to the series at the old index). In other words, it seems like even if I change index of array, it keeps writing into the old array index!
It's like equivalent to this (I know this sounds crazy but that is basically what I am getting):
int[] array = new int[5];
array[0] = 1;
array[1] = 2;
System.out.println(array[0]);
And the output I get is
2
This is something I have never heard of before, and I have code similar to this I wrote here in two other places, and in that two places it goes just fine, but in this third place I keep getting that exception.
Is this some kind of bug in JVM?
Does somebody know what this could be?
I don't know too much about TimeSeries, but after skimming the docs about it it says:
"The time series will ensure that (a) all data items have the same
type of period (for example, Day) and (b) that each period appears at
most one time in the series."
Link to Docs
I'm guessing the error is pretty straight forward or a misuse of TimeSeries. It looks like you are simply adding a duplicate date and that the constraints of TimeSeries don't allow that.
You may wish to consider writing a custom class that has the functionality you want. Yet again, I don't know much about TimeSeries, but I hope this helped a little.
Your for loop will always overwrite the value with an index of 0 on seriesArray.
What I mean is, the first time it will write to [0]
The second it will write to [0] then [1]
Is this intended?
I have not looked at the docs too much, but the message says 'the series already contains an observation for that time period.' I think that loop is not doing what you want it to do.

Set<String> treating [1.0,1] as different values

I am having a code sequence like this which is part of an Accuracy checking of a Data mining algorithm.
ie A trained data gets compared against some predicted values from my algorithm, and accuracy checking is done comparing both class labels.
say my values are [No,No],[No,Yes],[1.0,1],[1,1],[1,0] which are class labels
I am trying to compare the accuracy of my predicted data
public void reduce(Text key, Iterable<Text> values, Context context)
Set<String> set = new HashSet<String>();
for (Text val : values) {
set.add(val.toString());
}
int count = set.size();
if(count == 1){
System.out.println("Correct class label");
corClass++;
}
else{
System.out.println("InCorrect class label");
}
[No,No]: Correct class label
[No,Yes]: InCorrect class label
[1.0,1]: InCorrect class label
[1,1]: Correct class label
[1,0]:InCorrect class label
For me [1.0,1] this is falling into incorrect classlabel.
Set<String> set is treating [1.0,1] as different eventough they are equal but double and integer.
How to fix a workaround.
Please suggest
Thanks in advance.
You seem to have rules that your code doesn't respect. You say 1.0 is a "double". Is there a rule that determines under which conditions the code is a double? For example, is "1e10" a double -- 1 x 10^10? Or is it a string like "yes" presumably is?
1.0 and 1 are different strings. If you have some comparison rule that makes these two things identical, you'll have to implement it somewhere -- it won't happen by magic. It's not clear from your question precisely what the rule is, but whatever it is, implement it.
You're not storing a set of strictly strings, you're storing a set of both strings and integers. You don't know which one you're going to put in next, but you don't necessarily care about that; you're just leveraging the set properties for your use case.
What you can do instead of just create a set that stores most any object in it.
Set<?> set = new HashSet<>();
for (Text val : values) {
try {
set.add(Double.valueOf(val.toString()).intValue());
} catch (NumberFormatException nfe) {
set.add(val.toString());
}
}
It's not an attractive thing to do when we're talking about using exceptions as control flow, but this will get you past your immediate pain.
Currently, you are using a set of strings to store your data. Since it is a set of Strings, the set will allow any elements that are unequal strings. Wouldn't it be confusing if you were writing a different application, where you really needed string equality, if "1".equals("1.000")==true?
In this case, I think it would be better not to use a set at all...
This function should work properly for any number or string based equality:
public boolean stringOrDoubleEqual(String a,String b){
try{
//Change the 0.001 to the acceptable error for your application.
return Math.abs(Double.parseDouble(a)-Double.parseDouble(b))<0.001;
}catch(NumberFormatException e){
return a.equals(b);
}
}
I'm sure the rest should come naturally, if this fits your use case :)

Check for empty JFormattedTextField

I'm new here, and I'd like some help on a small Java project I'm doing. This is the code snippet I need help with:
private void CalculateButtonActionPerformed(java.awt.event.ActionEvent evt)
{
// TODO add your handling code here:
float Principal, Rate, Time, Result, Temp;
Principal = Float.valueOf(PrincipalTextField.getText());
Rate = Float.valueOf(RateTextField.getText());
Time = Float.valueOf(TimeTextField.getText());
Temp = (float) Math.pow((1 + Rate / 100), Time);
Result = Principal * Temp;
ResultTextField.setText(String.valueOf(Result));
}
I'd like to check if PrincipalTextField, OR RateTextField, OR TimeTextField aren't filled by the user, and if so, display a dialog box that asks him/her to recheck them. The text fields are JFormattedTextField variables. I realise that I can do this with a if/else or a while loop, but I'm not sure how to set about doing so. Please help!
You can do something like this:
The getText() returns you a String value. So you can always invoke length() and check whether the length comes to 0 or not. (*I would suggest calling trim() on the String before calling length() to remove any whitespaces)
Next if any of the length comes to be zero, what you want to do is display a Dialog Box. This you can do by calling JOptionPane.showMessageDialog(). You can read more about "How to Make Dialogs" over here.
So, you would do something like this:
String principalText = PrincipalTextField.getText();
String rateText = RateTextField.getText();
String timeText = TimeTextField.getText();
if(principalText.trim().length == 0 || rateText.trim().length == 0 || timeText.trim().length == 0){
JOptionPane.showMessageDialog(null, "YOUR_ERROR_MSG", "ERROR_TITLE", JOptionPane.ERROR_MESSAGE);
}
This might be off-topic, but I would suggest looking at Java Naming Convention. The convention for variables is to compose variable names using mixed case letters starting with a lower case letter
you miss reason for why there is JFormattedTextField
have to set Number Formatter for JFormattedTextField, then
you not need to parsing Float value (better could be to use double)
empty coudl be 0 (zero) value by default
take value in the form ((Number)PrincipalTextField.getValue()).floatValue();
look at code example for tutorial,
Also consider subclassing InputVerifier, as discussed in Validating Input. There's a related example here.

Categories

Resources