I want to generate random integers such that the next generated number is always greater than the previous one.
Assume I start with 3, I want the next to be always greater than 3. And say I generated 5, I want the next to be greater than 5 and so on..
This should get you a number that is consistently larger than the previous value. The range is the maximum distance from the previous value that you want the number to be.
public getLargerRandom(int previousValue){
int range = 100; //set to whatever range you want numbers to have
return random.nextInt(range) + previousValue;
}
int rnd = 0;
while (true) {
rnd = ThreadLocalRandom.current().nextInt(rnd +1, Integer.MAX_INT);
System.out.println("Next random: "+rnd);
}
You would store the randomly generated number as a variable, then use that as a minimum value for the next generation of numbers.
int x = 0;
x = new Random.nextInt(aNumber) + x;
The following example generates a set of random numbers between a start value and a max value without going over the desired maximum number.
import java.util.Random;
public class RandomNumbers {
public static void main(String[] args) {
GetIncreasingInts(20, 3, 101);
}
public static void GetIncreasingInts(int numIntsToGet, int start, int max) {
if (numIntsToGet > 0 && start >= 0 && max > 0) {
Random random = new Random();
int nextStart = start;
int num = -1;
for (int index = 0; index < numIntsToGet; index++) {
if ((max - 1) <= nextStart)
break;
else {
num = nextStart + random.nextInt(max - nextStart);
nextStart = num;
System.out.println("Number: " + num);
}
}
}
}
}
Related
Highly divisible triangular number, my solution
My solution of challenge from Project Euler takes too much time to execute. Although on lower numbers it works fine. Anyone could look up to my code and give me any advice to improve it?
The content of the task is:
The sequence of triangle numbers is generated by adding the natural numbers. So the 7th triangle number would be 1 + 2 + 3 + 4 + 5 + 6 + 7 = 28. The first ten terms would be:
1, 3, 6, 10, 15, 21, 28, 36, 45, 55, ...
Let us list the factors of the first seven triangle numbers:
(1: 1),
(3: 1,3),
(6: 1,2,3,6),
(10: 1,2,5,10),
(15: 1,3,5,15),
(21: 1,3,7,21),
(28: 1,2,4,7,14,28).
We can see that 28 is the first triangle number to have over five divisors.
What is the value of the first triangle number to have over five hundred divisors?
`public static void main(String[] args) {
int sum = 0;
int count = 0;
for (int i = 1; i <= Integer.MAX_VALUE; i++) {
sum += i;
for (int j = 1; j <= sum; j++) {
if (sum % j == 0) {
count++;
}
}
if (count > 500) {
System.out.println(sum);
break;
} else {
count = 0;
}
}
}`
Consider any set of primes (p1, p2, p3. . . pn) that factor a given number. Then the total number of divisors of that number are the products of (e1 + 1, e2 + 1, e3 + 1 ... en+1) where e is the exponent of the corresponding prime factor (i.e. the number of times that prime divides some number N).
There are three pieces to this answer.
The main driver code
the method to find the prime divisors.
and a Primes class that generates successive primes using an iterator.
The Driver
first instantiate the Primes class and initialize the triangleNo
Then continually generate the next triangular number until the returned divisor count meets the requirements.
Primes primes = new Primes();
long triangleNo = 0;
for (long i = 1;; i++) {
triangleNo += i;
int divisors = getDivisorCount(triangleNo, primes);
if (divisors > 500) {
System.out.println("No = " + triangleNo);
System.out.println("Divisors = " + divisors);
System.out.println("Nth Triangle = " + i);
break;
}
}
prints
No = 76576500
Divisors = 576
Nth Triangle = 12375 NOTE: this is the value n in n(n+1)/2.
Finding the prime factors
takes a value to factor and an instance of the Primes class
continues to test each prime for division, counting the number of times the remainder is 0.
a running product totalDivisors is computed.
the loop continues until t is reduced to 1 or the current prime exceeds the square root of the original value.
public static int getDivisorCount(long t, Primes primes) {
primes.reset();
Iterator<Integer> iter = primes;
int totalDivisors = 1;
long sqrtT = (long)Math.sqrt(t);
while (t > 1 && iter.hasNext()) {
int count = 0;
int prime = iter.next();
while (t % prime == 0) {
count++;
t /= prime;
}
totalDivisors *= (count + 1);
if (prime > sqrtT) {
break;
}
}
return totalDivisors;
}
The Primes class
A class to generate primes with a resettable iterator (to preserve computed primes from previous runs the index of an internal list is set to 0.)
an iterator was chosen to avoid generating primes which may not be required to obtain the desired result.
A value to limit the largest prime may be specified or it may run to the default.
Each value is tested by dividing by the previously computed primes.
And either added to the current list or ignored as appropriate.
if more primes are needed, hashNext invoked a generating to increase the number and returns true or false based on the limit.
class Primes implements Iterator<Integer> {
private int lastPrime = 5;
private List<Integer> primes =
new ArrayList<>(List.of(2, 3, 5));
private int index = 0;
private int max = Integer.MAX_VALUE;
public Primes() {
}
public Primes(int max) {
this.max = max;
}
#Override
public boolean hasNext() {
if (index >= primes.size()) {
generate(15); // add some more
}
return primes.get(index) < max;
}
#Override
public Integer next() {
return primes.get(index++);
}
private void generate(int n) {
outer: for (int candidate = lastPrime + 2;;
candidate += 2) {
for (int p : primes) {
if (p < Math.sqrt(candidate)) {
if (candidate % p == 0) {
continue outer;
}
}
}
primes.add(candidate);
lastPrime = candidate;
if (n-- == 0) {
return;
}
}
}
public void reset() {
index = 0;
}
}
Note: It is very likely that this answer can be improved, by employing numerical shortcuts using concepts in the area of number theory or perhaps even basic algebra.
I'm currently doing problem 3 from Project Euler. This the problem I need to solve:
What is the largest prime factor of the number 600851475143 ?
My code compiles as expected when I enter smaller numbers such as 10,000. But when I enter the number from the problem: 600851475143, nothing happens. Here is my code:
import java.util.ArrayList;
class problem3{
public static void main(String args[]){
ArrayList<Long> rr = findFactors(600851475143L);// rr holds an Array of factors.
rr = largestPrime(rr); // rr now holds an Array of factors that are prime.
int sizeOfrr = rr.size();
long largestPrimeFactor = rr.get(sizeOfrr-1);// prints the last(largest) prime factor
System.out.println(largestPrimeFactor);
/*This loops through all of the prime factors found
for(int i = 0; i<rr.size(); i++){
System.out.println(rr.get(i));
}*/
System.exit(0);
}
// This method returns an array of factors of the Long argument passed into parameter number.
public static ArrayList<Long> findFactors(Long number){
ArrayList<Long> factors = new ArrayList<Long>();
for(Long i= 1L; i<=number; i++){ // Divide number by every single digit upto and including itself
// Remember, we need to place L or l after an integer to let the compiler know its a long - not an int primitve.
if(number%i == 0){ // If number modules i is equal to zero, then i is a factor.
factors.add(i); // Append i to the factors array.
}
}
return factors;
}
// Increments the unit divisor, starting at 2L
/* The goal is to find if primeArray[i] has more than one factor. (Exluding 1 itself)
The loop begins at 2L. If primeArray[i]%j == 0, counter will increment by one.
The moment counter hits 2, we know primeArray[i] is not a prime since if it were prime,
the counter would be set to 1 and only 1 (because counter would only increment when j is
equal to primeArray[i] or in otherwords, when it is equal to itself. )
The method below returns an array of all the prime numbers
*/
public static ArrayList<Long> largestPrime(ArrayList<Long> primeArray){
int counter =0;
for(int i = 0; i<primeArray.size(); i++){ // Loops through the prime array
for(Long j = 2L; j<= primeArray.get(i); j++){
// (iL)??; jL++) { // 2L/3 for instance
if(primeArray.get(i)%j == 0){// Is it a factor?
counter++;
}
if(counter > 1){
primeArray.remove(i);
counter = 0;
break;
}
if(j == primeArray.get(i)){
counter = 0;
}
}
}
return primeArray;
}
}
nothing happens
As Qbrute said, you're looping 600851475143 times. It takes really a lot.
Since you have to find the largest prime factor, you don't need to find every factor, so you could skip every even number.
You could find first every prime factor and few others, then keep only the prime ones just comparing the ones you found each other.
Moreover the first loop can end at Math.sqrt(input). What about the (prime) factors above that? Just do input/factor.
Lastly you can keep your array sorted, this way you can stop looking for a prime after the first one. You should also use the primitive every time you can.
These optimization should be enough.
Try this:
public static void main(final String[] args) {
final long n = 600851475143L;
final long largestPrime = findLargestPrimeFactors(n);
System.out.println("The largest prime of " + n + " is: " + largestPrime);
}
public static long findLargestPrimeFactors(final long num) {
final List<Long> factors = new ArrayList<>();
int index = 0;
if ((num % 2L) == 0) {
factors.add(num / 2L);
factors.add(2L);
index = 1;
}
final long end = Double.valueOf(Math.floor(Math.sqrt(num))).longValue();
for (long i = 3L; i <= end; i += 2) { // skip every even number
if ((num % i) == 0) {
// This way the list is sorted in descending order
factors.add(index++, (num / i));
factors.add(index, i);
}
}
final long largestPrime = retainsLargestPrime(factors);
return largestPrime != 1L ? largestPrime : num; // if largestPrime is 1 it means that num is a prime number
}
private static long retainsLargestPrime(final List<Long> factors) {
long largestPrime = 1L;
if ((factors != null) && !factors.isEmpty()) {
final int size = factors.size();
for (int i = 0; (i < size) && (largestPrime == 1L); i++) {
boolean isPrime = true;
final long l = factors.get(i);
for (int j = i + 1; (j < size) && isPrime; j++) {
isPrime = !((l % factors.get(j)) == 0); // stop the inner loop as soon as possible
}
if (isPrime) {
largestPrime = l;
}
}
}
return largestPrime;
}
So Im trying to make a function that returns an arbitrary integer integer which is greater than X, not greater than 1,000,000,000 , and that ends with 0. You can assume that X is between 1 and 999,999,999. For example, given X = 33, your funcitonm may return 77 and for X = 22, your function may return 92.
Here is what I got so far, not sure if im even doing it right...
import java.util*;
import java.io*;
public class exerciseA {
public static void main(String[] args) throws Exception {
int max = 1000000000;
int min = 0;
int diff = max - min;
Random arbitrary = new Random();
int i = arbitrary.nextInt(diff + 1);
i += min;
System.out.print("The arbitrary Number is " + i);
}
}
The following snippet will do the trick:
int max = 100000000; // change made here
int min = 0;
int diff = max - min;
Random arbitrary = new Random();
int i = arbitrary.nextInt(diff + 1);
i += min;
System.out.print("The arbitrary Number is " + i * 10); // change made here
Note:
Initialize max to 100000000 as we will be multiplying the arbitrary number by 10.
I am trying to write a simple mastermind game where a 4 digit number will be randomly selected by the computer and the user inputs a number over and over again until the correct number is found. I am trying to do this by passing the guessed number and the random number to their own separate arrays and then comparing them, position by position to see if they are similar. If two numbers are in the exact same spot
Example:
if guessArray[0] == numsArray[0] then the computer will print a *.
If two numbers are present but not in the exact same spot (eg. you made a guess of 2056 but the actual number is 1203) then one + should be printed. This cycle repeats until the number is guessed.
I've already asked a friend in person what the problem was and he couldn't figure it out. He knows the most code out of my friends so this was my next place to go.
Here is the full project. I did not write the ConvertInt2Array method. I found it on the internet.
import java.util.Scanner;
import java.util.Arrays;
import java.util.Random;
public class Mastermind {
public static Random numGen = new Random();
public static void main(String [] args) {
Scanner Input = new Scanner (System.in);
int x = 0;
int number = 0;
int random = 0;
int guess = 0;
int y = 0;
int numArray[] = new int[4];
int guessArray[] = new int[4];
boolean isGuessed = false;
//Generate Random Number
for(x=0; x<=3; x++) {
int rand = Math.abs(numGen.nextInt());//Get the absolute value
random = (rand % 999 + 1);
numArray[x] = random;
number+=random;
}
while(isGuessed == false){
System.out.println("Guess a four digit random number");
guess = Input.nextInt();
guessArray = convertInt2Array(guess);
for(y=0; y<=3; y++) {
if(numArray[y] == guessArray[y]) {
System.out.print("*");
}
else if(Arrays.equals(numArray, y, y, guessArray, 0, guessArray.length) == true) {
System.out.print("+");
}
else {
}
if(guess==number) {
isGuessed = true;
}
}
}
System.out.println("You guessed it correctly!");
}
public static int[] convertInt2Array(int guess) {
String temp = Integer.toString(guess);
String temp2;
int temp3;
int [] gArray = new int[temp.length()];
for(int i=0;i<temp.length();i++) {
if (i!=temp.length()) {
temp2 = temp.substring(i, i+1);
} else {
temp2 = temp.substring(i);
}
temp3 = Integer.parseInt(temp2);
gArray[i] = temp3;
}
return gArray;
}
}
There may be more than one issue here, but here's a potential problem:
int rand = Math.abs(numGen.nextInt()); // Get the absolute value
random = (rand % 999 + 1);
This will usually result in random being a three-digit number. You mentioned you want this to be a four-digit number. Random.nextInt() can return any of the possible 232 integer numbers (from -2147483648 to 2147483647). To fix this, use a different Random.nextInt and specify your bounds:
int lowerBound = 1000;
int upperBound = 10000;
random = numGen.nextInt(upperBound - lowerBound) + lowerBound;
Let's break this down: numGen.nextInt(upperBound - lowerBound) evaluates to numGen.nextInt(9000), which will return a number between 0 (inclusive) and 9000 (exclusive), i.e. anything in the range 0-8999. You then add the lower bound of 1000 to ensure that random will be at least 1000 and up to 9999.
See the documentation for Random.nextInt(int bound).
Hopefully this gets you pointed in the right track.
How do I a get the counter to count the odd number under 100 in this program?
public class checkpassfail {
public static void main(String[] args) {
int sum =0;
double avr;
int lower = 1;
int uper = 100;
int num=lower;
int counter =0;
while( num <= uper){
sum= sum+(num+=3);
counter+=3;
}
System.out.println("the sum of these nubers is\t" +sum);
System.out.println(counter);
double s =(double)sum;
avr =s/counter;
System.out.println("the average of these nubers is \t"+avr);
}
What do you actually want to do?
If I'm not wrong you want to find odd numbers in between lower_bound and upper_bound.
int lower_bound = 0, upper_bound = 10;
ArrayList<Integer> odds = new ArrayList<Integer>();
while(lower_bound < upper_bound)
{
if(lower_bound % 2 == 1)
odds.add(lower_bound);
lower_bound++;
}
// Number of odd numbers found
int numberOfOddsFound = odds.size();
Welcome to StackOverflow :)
Using the for-loop, you calculate these aggregated values with:
final int lower = 1; // Lower bound
final int upper = 100; // Upper bound
int sum = 0; // Default sum
int count = 0; // Default count
double average = Double.NaN; // Default average
int i = lower; // Init the "runnig" variable
while (i <= upper){ // Until the upper bound is reached, do:
sum += i; // Add the number to the overall sum
count++; // One more number has been used - count it
i += 2; // Add 2 since you mind odd values only
}
average = sum / count; // Calculate the average
// And enjoy the results below
System.out.println("Count: " + count);
System.out.println("Sum: " + sum);
System.out.println("Average: " + average);
There also other ways of using the formulas to calculate these characteristics of a regular sequence of numbers or with Stream-API using IntStream.range(..) which allows calculating the aggregation values directly. However, in the beginning, stick with the for-loop.
You don't have to do all of this I guess. If you already know the highest value and the lowest value, and you want to count how many odd numbers between that range, you can code it like below.
int odd_count = (upper + 1) / 2 - lower / 2;
public class checkpassfail {
public static void main(String[] args) {
int lower = 1;
int upper = 100;
int odd_count = (upper + 1) / 2 - lower / 2;
System.out.println("Odd numbers count = "odd_count);
}
}
This will print Odd numbers count = 50.