java.util.Random and recursion in Java - java

I'd like to start off by saying this is a little more of a general question; not one pertaining to the specific examples that I have given, but simply a conceptual topic.
Example #1:
I'm creating a truly random string with UUID.java. Let's say I never want to have the same UUID generated, ever. Here's an idea of the circumstance:
(Let's assume that I'm saving/loading the List at the top- that's not the point)
Gist URL (I'm new to StackExchange- sorry!)
import java.util.ArrayList;
import java.util.List;
import java.util.UUID;
public class Example {
/**
* A final List<String> of all previous UUIDs generated with
* generateUniqueID(), turned into a string with uuid.toString();
*/
private static final List<String> PREVIOUS = new ArrayList<String>();
/**
* Generates a truly unique UUID.
*
* #param previous
* A List<String> of previous UUIDs, converted into a string with
* uuid.toString();
* #return a UUID generated with UUID.randomUUID(); that is not included in
* the given List<String>.
*/
public static UUID generateUniqueID(List<String> previous) {
UUID u = UUID.randomUUID();
if (previous.contains(u.toString())) {
return generateUniqueID(previous);
}
return u;
}
/**
* Generates a truly unique UUID using the final List<String> PREVIOUS
* variable defined at the top of the class.
*
* #return A truly random UUID created with generateUniqueID(List<String>
* previous);
*/
public static UUID generateUniqueID() {
UUID u = generateUniqueID(PREVIOUS);
PREVIOUS.add(u.toString());
return u;
}
}
Example #2: Okay, maybe UUID was a bad example, so let's use Random and a double. Here's another example:
Gist URL
import java.util.ArrayList;
import java.util.List;
import java.util.Random;
public class Example2 {
/**
* A final List<Double> of all previous double generated with
* generateUniqueDouble(), turned into a string with Double.valueOf(d);
*/
private static final List<Double> PREVIOUS = new ArrayList<Double>();
/**
* The RANDOM variable used in the class.
*/
private static final Random RANDOM = new Random();
/**
* Generates a truly unique double.
*
* #param previous
* A List<Double> of previous doubles, converted into a Double
* with Double.valueOf(d);
* #return a UUID generated with UUID.randomUUID(); that is not included in
* the given List<Double>.
*/
public static double generateUniqueDouble(List<Double> previous) {
double d = RANDOM.nextDouble();
if (previous.contains(Double.valueOf(d))) {
return generateUniqueDouble(previous);
}
return d;
}
/**
* Generates a truly unique double using the final List<Double> PREVIOUS
* variable defined at the top of the class.
*
* #return A truly random double created with generateUnique(List<Double>
* previous);
*/
public static double generateUnique() {
double d = RANDOM.nextDouble();
PREVIOUS.add(Double.valueOf(d));
return d;
}
}
The point: Is this the most efficient method of doing something like this? Keep in mind I gave you examples, so they're pretty vague. Preferrably I wouldn't like to use any libraries for this, but if they really are a substantial difference in efficency please let me know about them.
Please let me know what you think in the responses :)

I suggest you make the generated IDs sequential numbers instead of doubles or uuids. If you want them to appear random to end users, display the sha1 of the number in base64.

Some points have already been discussed in the comments. To summarize and elaborate them here:
It is very unlikely that you create the same double value twice. There are roughly 7*1012 different double values (assuming that the random number generator can deliver "most" of them). For the UUIDs, the chance of creating the same value twice is even lower, since there are 2122 different UUIDs. If you created enough elements to have a non-negligible chance for a collision, you'd run out of memory anyhow.
So this approach does not make sense in practice.
However, from a purely theoretical point of view:
Performance
Using a List for this operation is not optimal. The "best case" (and by far the most common case) for you is that the new element is not contained in the list. But for the check whether the element is contained, this is the worst case: You'll have to check each and every element of the list, only to detect that the new element was not yet present. This is said to be linear complexity, or for short, O(n). You could use a different data structure where checking whether an element is contained can be done more quickly, namely in O(1). For example, you could replace the line
private static final List<Double> PREVIOUS = new ArrayList<Double>();
with
private static final Set<Double> PREVIOUS = new HashSet<Double>();
Performance and Correctness
(referring to the recursive approach in general here)
Performance
From a performance point of view, you should not use recursion when it can easily be replaced by an iterative solution. In this case, this would be trivial:
public static double generateUniqueDouble(List<Double> previous) {
double d = RANDOM.nextDouble();
while (previous.contains(d)) {
d = RANDOM.nextDouble();
}
PREVIOUS.add(d);
return d;
}
(it could be written a bit more compact, but that does not matter now).
Correctness
This is more subtle: When there are many recursive calls, then you might end up with a StackOverflowError. So you should never use recursion unless you can prove that the recursion will end (or better: That it will end "after a few steps").
But here's your main problem:
The algorithm is flawed. You cannot prove that it will be able to create a new random number. The chance that even a single new element is already contained in the collection of PREVIOUS elements is ridiculously low for double (or UUID) values. But it is not zero. And there is nothing preventing the random number generator from creating the random number 0.5 indefinitely, trillions of times in a row.
(Again: These are purely theoretical considerations. But not as far away from practice as they might look at the first glance: If you did not create random double values, but random byte values, then, after 256 calls, there would be no "new" values to return - and you would actually receive the StackOverflowError...)

It would be better to use a hash table than a list. Generate your candidate value, check for a collision in the hash table, and accept it if there is no collision. If you use a list, generating a new value is an O(n) operation. If you use a hash table, generating a new value is an O(1) operation .

Related

Fibonacci Heap for Dijkstra via Java

I want to implement Fibonacci Heap on Dijkstra Algorithm. I use this code for Fibonacci heap.
http://keithschwarz.com/interesting/code/?dir=fibonacci-heap
The problem is how to call the method: decreaseKey? It always give me the hint that (entry,double). But how to write an entry? The following is a simple example, how to fill the question mark?
FibonacciHeap<Integer> aa = new FibonacciHeap<>();
aa.enqueue(10, 1.01);
aa.enqueue(10, .2);
aa.enqueue(12, 3.2);
aa.enqueue(13, 3.4);
aa.decreaseKey(??????, newPriority);
decreaseKey() expects the first argument to be of type FibonacciHeap.Entry. 3 methods in the class return the Entrys of the heap:
public Entry<T> enqueue(T value, double priority);
public Entry<T> min();
public Entry<T> dequeueMin();
Each of the 3 methods return a different element, and modify the heap in their own way. Depending on your use case, you can store these Entrys in a variable and pass it to decreaseKey().
One such case would be storing the Entry while enqueuing it. Whenever you enqueue() something to the heap, it returns its corresponding Entry. From its documentation:
/**
* Inserts the specified element into the Fibonacci heap with the specified
* priority.
* ...
* #return An Entry representing that element in the tree.
*/
public Entry<T> enqueue(T value, double priority);
You can store it, and pass it to decreaseKey().
FibonacciHeap<Integer> aa = new FibonacciHeap<>();
FibonacciHeap.Entry entry = aa.enqueue(10, 1.01);
// ...
aa.decreaseKey(entry, newPriority);

forEach() is not supposed to respect ordering, but here it seems to respect, why?

I have been trying to do a little basic GA implementation myself. I used a class Gene which wraps a binary bit, a Chromosome class that has an ArrayList named genes of Gene objects. In the Chromosome class I have an evaluation method value() that simply computes the decimal equivalent of the bits in the chromosome. The overridden toString() method in Chromosome class uses a lambda expression to create a String representation of the bits in the Gene objects contained in the ArrayList genes. My question is: since forEach() method is not supposed to respect the ordering (for the benefit of parallelism), why does it always return the correct string representation of the underlying bits, i.e. in the order in which they were created? Or am I missing something serious here? May it be because of very short chromosome length, that the 'disrespecting' of the ordering is not prominent here?
Here are my classes.
The Gene class
public class Gene {
private short value;
public Gene() {
value = (short) (Math.random() <= 0.5 ? 0 : 1);
System.out.print(value);
}
#Override
public String toString() {
return String.valueOf(value);
}
}
The Chromosome class
import java.util.ArrayList;
import java.util.Arrays;
public class Chromosome {
private ArrayList<Gene> genes;
public Chromosome(int numOfGene) {
this.genes = new ArrayList<>();
for (int i = 0; i < numOfGene; i++) {
this.genes.add(i, new Gene());
}
}
public int value() {
return Integer.parseInt(this.toString(), 2);
}
#Override
public String toString() {
StringBuilder chromosome = new StringBuilder("");
genes.stream().forEach((g) -> chromosome.append(g));
return chromosome.toString();
}
public static void main(String[] args) {
Chromosome c = new Chromosome(10);
System.out.println("");
System.out.println(c);
}
}
The print statement in Gene constructor is to see the order in which the genes were created. No matter how many times I run the program, the forEach() always gives the correct representation of the bits, which is confusing for me. Or am I completely ignorant of how this is supposed to work, I know not :-(
Since you are using a sequential Stream, the order of the input list is preserved. If you change it to
genes.parallelStream().forEach((g) -> chromosome.append(g));
You would probably get a different order.
Since genes is an ArrayList, and a List is ordered, you are basically printing the List according to how you added the stuff to it. Basically, the first to be printed is the first that was inputted.
If it was a parallelStream, the order would be random.
Takes a look at this link which explains the forEach in an excellent way.
Excellent answers given! But I would like to add this for future readers, as I found this stated very clearly in the link given by bajada93.
When you create a stream, it is always a serial stream unless otherwise specified. To create a parallel stream, invoke the operation Collection.parallelStream.
Which means forEach will iterate such collection in the order it was constructed.
Link: JavaSE tutorial

Infinite Integer in Java

I don't think I'm approaching this the right way. I'm supposed to create a class that allows users to enter in any number not matter how big it is (Of course, with the restrictions of memory it's not really infinite). I have some code but I'm pretty sure the quality is crap. I seem to be having the most trouble with a string and have been avoiding it. I'll only post what I have worked on. I just need help clearing it up because I don't think I'm going in the right direction. Here is what my code has so far. I apologize. I'm not a very seasoned coder.:
public class InfiniteInteger implements Comparable<InfiniteInteger> {
// TO DO: Instance Variables
public final int BigNumbers;
public final String Infinite;
public final int []integerArray;
public InfiniteInteger(String s) {
// TO DO: Constructor
Infinite=s;
}
public InfiniteInteger(int anInteger) {
// TO DO: Constructor
BigNumbers=anInteger;
integerArray= new int[anInteger];
}
public int getNumberOfDigits() {
// TO DO: return an integer representing the number of digits
of this infinite integer. //
int NumberOfDigits=0;
for(int i=0; NumberOfDigits<0;i++){
}
return BigNumbers;
}
/**
* Checks whether this infinite integer is a negative number.
* #return true if this infinite integer is a negative number.
* Otherwise, return false.
*/
public boolean isNegative() {
// TO DO
if(isNegative()) {
return true;
} else return false;
}
Do I need to convert the string to int in my first constructor. I also had made an array previously in the string constructor but it caused a whole lot of grief so I got rid of it and just put one in the second constructor.
You can use a BigInteger for that. It uses an bitarray with varying length.
Operations on BigInteger's are slower but will work, regardless of the number (as long as it is an integer). And furthermore BigInteger operations are optimized (for instance using special CPU instructions)...
On a sidenote if people mean any number, they sometimes mean any resonable number. In that case the range of a long is in many cases sufficient.
Use the Java built-in class BigInteger, from the Javadoc BigInteger is for
Immutable arbitrary-precision integers.
What you are trying to accomplish is already made in BigInteger class. Maybe examining it's source might be useful when creating a simpler version of it :
http://grepcode.com/file/repository.grepcode.com/java/root/jdk/openjdk/6-b14/java/math/BigInteger.java

Organize similar functions in a class

I have a method that gets a matrix of 11xm values (m is variable), analyzes the data and returns an array of features based on that matrix.
I've already written a long function to process this data, however, I wanted to convert it to a class since I will need to extend it later.
My issue is related to how I should organize some functions.
I thought about having a "get" function for each feature extracted from the raw data.
the problem is that different functions will need the same exact preliminary calculations.
For example, I have many x&y points, and I will first need to calculate the pairwise distances, then velocities, then accelerations, and angles. Then all this data will be used to calculate some features.
For example, in the following, if I need to call preliminary1 for both feature 1 & 2, that's twice the work, and I might actually need the same preliminary calculations for 4 or 5 subsequent features (functions). I might need some more calculations for feature 3 that would also need preliminary 1.
Any ideas on how to do this?
private double[] preliminary1(double[], double[]) { some calculations}
private double[] preliminary2(double[]) {
value = preliminary1(value1, value2);
// more calcuations }
public double getFeature1() {
value = preliminary1(value1, value2);
// more calcuations }
public double getFeature2() {
value = preliminary1(value1, value2);
// more calcuations }
public double getFeature3() {
value = preliminary2(value1);
// more calcuations }

Does guava have an equivalent to Python's reduce function?

Does guava (or another java library) have something like reduce() function in Python?
I'm looking for something like this http://docs.python.org/library/functions.html#reduce
No. It might eventually, though functional stuff like that isn't a core focus of Guava. See this issue.
I've not (yet) managed to find any Java collections libraries that support map and reduce. (I exclude map/reduce functionality in parallel / distributed processing frameworks ... because you need a "big" problem for these frameworks to be worthwhile.)
Probably, the reason for this "lack" is that map/reduce coding without closures is just too cumbersome. Too much boilerplate code, too much heavy-weight syntax. Since the main point of using map / reduce primitives on simple collections is to make your code simple and elegant ...
#CurtainDog contributed a link to lambdaj. That does the kind of thing that the OP is after (though there's no method specifically called reduce). But it illustrates what I was saying about boilerplate. Notice that many of the higher order operations involve creating classes that extend one or other of the Closure classes.
(FWIW, I think that the Lambda.aggregate(...) methods are the lambdaj analog of reduce.)
Java 8 streams allow you to do this.
mylist.stream().map((x) -> x + 1).reduce((a,b) -> a + b)
For more information: http://docs.oracle.com/javase/8/docs/api/java/util/stream/package-summary.html
I have recently submitted an issue where I requested / discussed something similar. This is what would be needed in my implementation
/**
* Aggregate the selected values from the supplied {#link Iterable} using
* the provided selector and aggregator functions.
*
* #param <I>
* the element type over which to iterate
* #param <S>
* type of the values to be aggregated
* #param <A>
* type of the aggregated value
* #param data
* elements for aggregation
* #param selectorFunction
* a selector function that extracts the values to be aggregated
* from the elements
* #param aggregatorFunction
* function that performs the aggregation on the selected values
* #return the aggregated value
*/
public static <I, S, A> A aggregate(final Iterable<I> data,
final Function<I, S> selectorFunction,
final Function<Iterable<S>, A> aggregatorFunction){
checkNotNull(aggregatorFunction);
return aggregatorFunction.apply(
Iterables.transform(data, selectorFunction)
);
}
(The selector function can pull the value to aggregate from the object to query, but in many cases it will be Functions.identity(), i.e. the object itself is what's aggregated)
This is not a classic fold, but it requires a Function<Iterable<X>,X> to do the work. But since the actual code is a one-liner, I have instead chosen to request some standard aggregator functions (I'd put them in a class called something like Aggregators, AggregatorFunctions or even Functions.Aggregators):
/** A Function that returns the average length of the Strings in an Iterable. */
public static Function<Iterable<String>,Integer> averageLength()
/** A Function that returns a BigDecimal that corresponds to the average
of all numeric values passed from the iterable. */
public static Function<Iterable<? extends Number>,BigDecimal> averageOfFloats()
/** A Function that returns a BigInteger that corresponds to the average
of all numeric values passed from the iterable. */
public static Function<Iterable<? extends Number>,BigInteger> averageOfIntegers()
/** A Function that returns the length of the longest String in an Iterable. */
public static Function<Iterable<String>,Integer> maxLength()
/** A Function that returns the length of the shortest String in an Iterable. */
public static Function<Iterable<String>,Integer> minLength()
/** A Function that returns a BigDecimal that corresponds to the sum of all
numeric values passed from the iterable. */
public static Function<Iterable<? extends Number>,BigDecimal> sumOfFloats()
/** A Function that returns a BigInteger that corresponds to the integer sum
of all numeric values passed from the iterable. */
public static Function<Iterable<? extends Number>,BigInteger> sumOfIntegers()
(You can see my sample implementations in the issue)
That way, you can do things like this:
int[] numbers = { 1, 5, 6, 9, 11111, 54764576, 425623 };
int sum = Aggregators.sumOfIntegers().apply(Ints.asList(numbers)).intValue();
This is definitely not what you are asking for, but it would make like easier in many cases and would overlap with your request (even if the approach is different).
Jedi has a reduce operation. Jedi also helps reduce the boiler plate by using annotations to generate functors for you. See these examples.
Guava has transform (map). Seems like reduce is missing though?
I have developed a library to do map/filter/reduce with standard J2SE.
Sorry it is in french, but with google translate you can read it :
http://caron-yann.developpez.com/tutoriels/java/fonction-object-design-pattern-attendant-closures-java-8/
You can use if like this :
int sum = dogs.filter(new Predicate<Arguments2<Dog, Integer>>() {
#Override
public Boolean invoke(Arguments2<Dog, Integer> arguments) {
// filter on male
return arguments.getArgument1().getGender() == Dog.Gender.MALE;
}
}).<Integer>map(new Function<Integer, Arguments2<Dog, Integer>>() {
#Override
public Integer invoke(Arguments2<Dog, Integer> arguments) {
// get ages
return arguments.getArgument1().getAge();
}
}).reduce(new Function<Integer, Arguments2<Integer, Integer>>() {
#Override
public Integer invoke(Arguments2<Integer, Integer> arguments) {
// sum âges
return arguments.getArgument1() + arguments.getArgument2();
}
});
System.out.println("Le cumul de l'âge des mâles est de : " + sum + " ans");
Enjoy this help
Use Totally Lazy, it implements all of those things an even more.
It basicly copied the whole funcional approach from Clojure.

Categories