How to create random value between two different sets of numbers - java

I am trying to generate a random character between the following two sets of unicode U+0020 to U+007E and U+00A0 to U+00FF. I have created the code to generate a value between U+00A0 to U+00FF but I also need my generator to include the values from U+00A0 to U+00FF, how is this possible? Any help is greatly appreciated, here is what I have so far. (P.S. I am using seed for testing). For example instead of just trying to create a integer between 1-10, I would like to know how to create a random number that could either be between 1-10 or 50-100.
private static char random(){
long seed = 1776;
Random number = new Random(seed);
int randomNumber = number.nextInt(126) + 32;
char a = (char) randomNumber;
return a;
}

To generate a random number to fall in multiple ranges, you first calculate the total number of values in your target dataset, then generate a random number for that total, and assign it to the appropriate set.
Sample code to generate 20 random numbers in ranges 0x20 - 0x7E and 0xA0 - 0xFF, inclusive:
int low1 = 0x20, high1 = 0x7E, low2 = 0xA0, high2 = 0xFF;
int count1 = high1 - low1 + 1;
int count2 = high2 - low2 + 1;
long seed = 1776;
Random rnd = new Random(seed);
for (int i = 0; i < 20; i++) {
int n = rnd.nextInt(count1 + count2);
if (n < count1) { // random number is for range 1
n = n + low1; // offset into range 1
} else { // random number is for range 2
n = n - count1 + low2; // offset into range 2
}
System.out.printf("%02X ", n);
}
Sample Output
6B 6B A5 DA B3 F7 2B C6 AB F2 3F EE F9 A5 28 31 AD D3 66 B0

Related

Java: Generating "00" as a possible Math.random output

I'm creating a "roulette wheel" for a programming class assignment. This wheel generates random numbers from 0 to 36 using Math.random. One part of the assignment is to add "double zero" (00) as a possible output. Is it possible to do so through this equation?
spin = (int) (Math.random()*(37 - 0)) + 0;
Assuming you want 00 and 0 to be a separate output, you will need to get a String instead, as integers treat the two as the same value. An option I thought of is to use a 39th possible output. You could add this in your code below:
String getSpin() {
int spin = (int)(Math.random() * 38);
if (spin == 38) return "00";
else return Integer.toString(spin);
}
When you want to print 00 you should take 0 convert it to string and add "0" to it and print it as 00 and in the application logic use only one 0 and make the app give it double change of hitting it
"00" can be NOT integer in Java so we can use String type for "00".
I thought we can prepare String array contains numbers as string from 00 to 36, then generate random number from 0 to 37 because length of string array is 38.
And then get a value from array at position for the random number.
I coded and put it in this answer, hope it can help you.
Cheers your assignment.
public static void main(String[] args) {
// Generate numbers as String from 00 to 36
String numbers[] = new String[38];
numbers[0] = "00";
for(int i=1; i<numbers.length; i++) {
numbers[i] = Integer.toString(i-1);
}
// Generate random number
int min = 0;
int max = numbers.length - 1;
int randomNum = min + (int)(Math.random() * ((max - min) + 1));
// Return number at a position of randomNum
System.out.println("Output: " + numbers[randomNum]);
}

Calculating the ISBN Number check digit using Java [closed]

Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 6 years ago.
Improve this question
I'm trying to calculate any ISBN-13 Number's Check Digit, I'm not too worried if the ISBN number is valid or invalid, but what I've been trying to do is get the code to work. There are obviously flaws in my interpretation of the algorithm, suggestions on how to fix it are welcome but the primary problem is receiving user input that is too large for an integer variable but I also want to avoid the decimals of the double value.
I already tried to use the BigDecimal and BigNumber but I simply don't have enough experience to be able to understand them completely. This is the algorithm to find d13 (the Check Digit): 10-(d1 +3d2 +d3 +3d4 +d5 +3d6 +d7 +3d8 +d9 +3d10 +d11 +3d12)%10.
The Code is a mess I know. I've used this website as a reference to what I want to do and I've been using this ISBN number as my practice: 9780132130806.
Again my question is how can I print the final ISBN number without decimals and how can I possibly fix my algorithm? (I'd also really appreciate any tips on a website that helps with teaching JOption as that is the prefered method i use because it looks a bit cleaner to me than using the scanner)
import javax.swing.JOptionPane;
import java.math.BigInteger;
public class ISBN
{
//George Sayegh Calculate check Digit ISBN
public static void main(String[] args)
{
//Define Variables
double ISBN12, D1, D2, D3, D4, D5, D6, D7, D8, D9, D10, D11, D12 = 0, D13;
double A = 100000000000L;
double B = 10000000000L;
double C = 1000000000;
double D = 100000000;
double E = 10000000;
double F = 1000000;
double G = 100000;
double H = 10000;
double I = 1000;
double J = 100;
double K = 10;
double L = 1;
//Get ISBN #
String ISBN12text = JOptionPane.showInputDialog("Please enter the first 12 digits of your ISBN number");
ISBN12 = Double.parseDouble(ISBN12text);
//Calculate D1
D1 = ((ISBN12 - (ISBN12 % A)) / A);
//Calculate D2
D2 = ((ISBN12 - (ISBN12 % B)) / B);
//Calculate D3
D3 = ((ISBN12 - (ISBN12 % C)) / C);
//Calculate D4
D4 = ((ISBN12 - (ISBN12 % D)) / D);
//Calculate D5
D5 = ((ISBN12 - (ISBN12 % E)) / E);
//Calculate D6
D6 = ((ISBN12 - (ISBN12 % F)) / F);
//Calculate D7
D7 = ((ISBN12 - (ISBN12 % G)) / G);
//Calculate D8
D8 = ((ISBN12 - (ISBN12 % H)) / H);
//Calculate D9
D9 = ((ISBN12 - (ISBN12 % I)) / J);
//Calculate D10
D10 = ((ISBN12 - (ISBN12 % K)) / K);
//Calculate D11
D11 = ((ISBN12 - (ISBN12 % L)) / L);
//Get D13
D13 = 10 - (D1 + (3 * D2) + D3 + 3 * D4 + D5 + 3 * D6 + D7 + 3 * D8 + D9 + 3 * 10 + D11 + 3 * D12) % 10;
JOptionPane.showMessageDialog(null, D1 +""+ D2 +""+ D3 +""+ D4 +""+ D5 +""+ D6 +""+ D7 +""+ D8 +""+ D9 +""+ D10 +""+ D11 +""+ D12 +""+ 13);
}
}
Try this extremely simple algorithm (written in Python, but it should be very easy to convert to Java). The comments hopefully explain enough. Should convert to not more than 10 lines (not including blank lines for readability)
#// Valid ISBN-12 string from user (12 numbers, doesn't matter what other characters)
isbn12 = '978-0-306-40615' #// Input it from the user, hardcoded Wikipedia example for testing
coeff = 1 #// Multiple used in calculating sum
sum = 0
for d in isbn12: #// Equivalent to for(char d : isbn12.toCharArray())
#// this next block is just a tryParse or an isDigit check
#// if the character is a digit, parse it to an int
#// else continue to next iteration
try:
#// just reassigning the value because-
#// Hey, this is Python!
d = int(d)
except ValueError:
continue
#// Add to sum after multiplying with coeff
sum += d * coeff
#// If coeff was 1, change to 3 and vice versa
#// Equivalent to coeff == 1 ? 3 : 1 in Java
coeff = 3 if coeff == 1 else 1
#// END FOR LOOP
#// Get positive number to be added to make ISBN divisible by 10
#// The extra % 10 at the end is for changing 10 to 0 without if
check_digit = (10 - sum % 10) % 10
(The extra // at the start of each comment is to make SO code formatting think it is a comment)
Here's a much simpler implementation based on this Wikipedia example. It lacks sanity checks---such as whether the input string is a valid ISBN13---but should be enough to get you going. I hope it helps.
Note that the input is an ISBN-13 string with the check digit removed (e.g. 978013213080 instead of 9780132130806); the program prints the check digit on the output; you should be able modify it if this is not what you want.
public class CheckISBN13 {
/* We assume isbnString is a *valid* ISBN-13 with the check digit removed. */
public static int[] stringToInt(String isbnString) {
int[] isbnInt = new int[12];
int j = 0;
for (int i = 0; i < isbnString.length(); ++i) {
if (Character.isDigit(isbnString.charAt(i))) {
isbnInt[j++] = Character.getNumericValue(isbnString.charAt(i));
}
}
return isbnInt;
}
public static int getCheckDigit(int[] isbnInt) {
int val = 0;
for (int i = 0; i < isbnInt.length; ++i) {
int coeff = (i % 2 == 0 ? 1 : 3);
val += coeff * isbnInt[i];
}
return 10 - (val % 10);
}
public static void main(String[] args) {
if (args.length < 1) {
System.err.println("Usage: java CheckISBN13 978-0-306-40615");
System.exit(-1);
}
String isbnString = args[0];
int[] isbnInt = stringToInt(isbnString);
System.out.println("Check digit: " + getCheckDigit(isbnInt));
}
}

Java addition giving wrong answer

I am trying to add four integers ie 4+3+2+1 but i get the value 202
class Task3{
public static void main (String args[]){
String x=(args[0]);
int I = Integer.parseInt (x);
char c1 = x.charAt(0);
char c2 = x.charAt(1);
char c3 = x.charAt(2);
char c4 = x.charAt(3);
System.out.println("First and last digit is: " + c1 +"," + c4);
if (c1 > c4)
System.out.println("The first digit is larger");
else
System.out.println("The second digit is larger");
int sum = c1 + c2 + c3 + c4;
System.out.println(sum);
}
}
replace char c1 = x.charAt(0); with Character.getNumericValue(x.charAt(0))
This is because you are adding numeric values of UNICODE code points, not digits represented by the corresponding characters.
In order to get a digit from a character code, call Character.digit(c1, 10) (ten indicates that you want a decimal digit).
int c1 = Character.digit(x.charAt(0), 10);
int c2 = Character.digit(x.charAt(1), 10);
int c3 = Character.digit(x.charAt(2), 10);
int c4 = Character.digit(x.charAt(3), 10);
Change
int sum = c1 + c2 + c3 + c4;
to
int sum = c1 + c2 + c3 + c4 - 4 * '0';
Since c1, c2, c3, c4 are all characters, so a digit say. 4 is taken as '4' that is basically the ASCII value, so to get 4 and not '4' you need to subtract '0' from each of c1, c2, c3, c4, so 4 * '0' subtracted
You are trying to sum up the chars ASCII codes and not the digit values. You have to retrieve the corresponding digit for each character and then evaluate you addition result:
class Task3
{
public static void main (String args[])
{
String x=(args[0]);
int I = Integer.parseInt (x);
char c1 = x.charAt(0);
char c2 = x.charAt(1);
char c3 = x.charAt(2);
char c4 = x.charAt(3);
int i1 = Character.digit(c1, 10);
int i2 = Character.digit(c2, 10);
int i3 = Character.digit(c3, 10);
int i4 = Character.digit(c4, 10);
System.out.println("First and last digit is: " + i1 +"," + i4);
if (i1 > i4)
System.out.println("The first digit is larger");
else
System.out.println("The second digit is larger");
int sum = i1 + i2 + i3 + i4;
System.out.println(sum);
}
}
The reason of the wrong output others already explained it now one of the way to get the correct output
int sum =0;
while(I>0){
int rem = I%10;
sum+=rem;
I = I/10;
}
System.out.println(sum);
I presume you are passing "4321" or similar to the program.
c1 will not be the number 1 but actually the Unicode number representing the character '1' which is actually 31 (in hexadecimal). The latest addition is adding these Unicode numbers.
See http://unicode-table.com/en/ for the list of unicode numbers to characters and also http://docs.oracle.com/javase/tutorial/i18n/text/unicode.html for more details of characters in Java.

Finding the last two digits before the decimal point for the number (4+sqrt(11))^n

I am doing a problem in which I have to find the last two digits before the decimal point for the number [4 + sqrt(11)]n.
For example, when n = 4, [4 + sqrt(11)]4 = 2865.78190... the answer is 65. Where n can vary from 2 <= n <= 109.
My solution - I have tried to build a square root function which calculate the sqrt of 11
which a precision equal to value of n input by the user.
I have used BigDecimal in Java to avoid overflow problems.
public class MathGenius {
public static void main(String[] args) {
Scanner reader = new Scanner(System.in);
long a = 0;
try {
a = reader.nextInt();
} catch (Exception e) {
System.out.println("Please enter a integer value");
System.exit(0);
}
// Setting precision for square root 0f 11. str contain string like 0.00001
StringBuffer str = new StringBuffer("0.");
for (long i = 1; i <= a; i++)
str.append('0');
str.append('1');
// Calculating square root of 11 having precision equal to number enter
// by the user.
BigDecimal num = new BigDecimal("11"), precision = new BigDecimal(
str.toString()), guess = num.divide(new BigDecimal("2")), change = num
.divide(new BigDecimal("4"));
BigDecimal TWO = new BigDecimal("2.0");
BigDecimal MinusOne = new BigDecimal("-1"), temp = guess
.multiply(guess);
while ((((temp).subtract(num)).compareTo(precision) > 0)
|| num.subtract(temp).compareTo(precision) > 0) {
guess = guess.add(((temp).compareTo(num) > 0) ? change
.multiply(MinusOne) : change);
change = change.divide(TWO);
temp = guess.multiply(guess);
}
// Calculating the (4+sqrt(11))^n
BigDecimal deci = BigDecimal.ONE;
BigDecimal num1 = guess.add(new BigDecimal("4.0"));
for (int i = 1; i <= a; i++)
deci = deci.multiply(num1);
// Calculating two digits before the decimal point
StringBuffer str1 = new StringBuffer(deci.toPlainString());
int index = 0;
while (str1.charAt(index) != '.')
index++;
// Printing output
System.out.print(str1.charAt(index - 2));
System.out.println(str1.charAt(index - 1));
}
}
This solution works up to n = 200, but then it begins to slow down. It stops working for n = 1000.
What is a good method to deal with problem?
2 -- 53
3 -- 91
4 65
5 67
6 13
7 71
8 05
9 87
10 73
11 51
12 45
13 07
14 33
15 31
16 85
17 27
18 93
19 11
20 25
21 47
22 53
23 91
24 65
25 67
At n=22 the results seem to repeat from the position of n=2.
So keep those 20 values in an array in the same order as in your list e.g. nums[20].
Then when the user provides an n:
return nums[(n-2)%20]
There is now a proof of this pattern repeating here.
Alternatively, if you insist on computing at length; since you calculating the power by looping multiplication (and not BigDecimal pow(n)) you could trim the number you are working with at the front to the last 2 digits and the fractional part.
Here is a much simpler solution for you...
Use the rational representation of 4+sqrt(11):
BigInteger hundred = new BigInteger("100");
BigInteger numerator = new BigInteger("5017987099799880733320738241");
BigInteger denominator = new BigInteger("685833597263928519195691392");
BigInteger result = numerator.pow(n).divide(denominator.pow(n)).mod(hundred);
UPDATE:
As you've mentioned in the comments below, this procedure is prone to precision-loss, and will eventually yield an incorrect result. I found this question to be rather interesting on the mathematical aspect, and so I published a question on MO (https://mathoverflow.net/q/158420/27456).
You can read the answer at https://mathoverflow.net/a/158422/27456.

My puzzle on Project Euler # 25 about java.lang.NullPointerException

I am working on the Project Euler #25. I am intending to save all fibonacci number in a BigInteger array. However, there throws a NullPointerException, I don't know why and how to avoid it. I know there is much more simple algorithm to solve this question. But I just want to know where is my mistake, thank you very much! Here is the question states: The Fibonacci sequence is defined by the recurrence relation:
Fn = Fn−1 + Fn−2, where F1 = 1 and F2 = 1. Hence the first 12 terms will be:
F1 = 1 F2 = 1 F3 = 2 F4 = 3 F5 = 5 F6 = 8 F7 = 13 F8 = 21 F9 = 34 F10 = 55 F11 = 89 F12 = 144 The 12th term, F12, is the first term to contain three digits.
What is the first term in the Fibonacci sequence to contain 1000 digits?
My code is below:
private static BigInteger[] fibonacci;
public static void main(String[] args) {
for(int i = 0; fibonacci[fibonacci.length-1].toString().length() < 1000; i++){
if(i == 0)
fibonacci[i] = BigInteger.ZERO;
if(i < 3)
fibonacci[i] = BigInteger.valueOf(1);
else
fibonacci[i] = fibonacci[i - 1].add(fibonacci[i - 2]);
}
System.out.println(fibonacci.length);
}
You have not initialized the array fibonacci. You need to allocate memory before using the array.
private static BigInteger[] fibonacci = new BigInteger[1000]; // Some number x
I would recommend using a List instead of an array given that you don't know the size of array.
private static List<BigInteger> fibonacci = new ArrayList<BigInteger>();
Also, if you are using arrays, fibonacci[fibonacci.length - 1] will not work because you are always checking for position 999 if you're initializing array size to 1000. For this to work, you have to use an ArrayList and then you can use
fibonacci[fibonacci.size() - 1]
You never initialized your fibonacci array.
Just use
private static BigInteger[] fibonacci = new BigInteger[1000]();
or better extract the amount of Fibonacci numbers you want to calculate to a separate constant:
private static int amount = 1000;
private static BigInteger[] fibonacci = new BigInteger[amount]();;
public static void main(String[] args) {
for(int i = 0; i < amount; i++){
if(i == 0)
fibonacci[i] = BigInteger.ZERO;
else if(i < 3)
fibonacci[i] = BigInteger.valueOf(1);
else
fibonacci[i] = fibonacci[i - 1].add(fibonacci[i - 2]);
}
System.out.println(fibonacci.length);

Categories