I am working at a programm right now where I need to sort an array of numbers ranging from 0 to 99999. In order to do so, one part of the task is to extract the digits from every number of the array, and that can be accomplished by
i = number / digit.
For example, for the number 23456, I am supposed to start by extracting the number 2, which can be done by using
digit = 10000
and calculating
i = 23456 / 10000 = 2.
A recursive call is then supposed to look at the next digit, so in this case we want to get
i = 23456 / digit = 3
and so on. I know that there are certain methods for this, but how can this be done with using only primitves? I already tried to play around with modulo and dividing the digit, but it's not giving any desired result.
Basic Formula
The n-th digit of a non-negative, integral, decimal number can be extracted by the following formula:
digit = ((num % 10^n) / 10^(n-1))
where % represents modulo division, / represents integer division, and ^ represents exponentiation in this example. Note that for this formula, the number is indexed LSD->MSD starting from 1 (not 0).
This formula will also work for non-decimal numbers (e.g. base 16) by changing 10 to the desired base. It will also work for negative numbers provided that absolute value of the final digit is taken. Finally, it can even function to extract the integer digits (but not fractional digits) of a floating point number simply by truncating and casting the floating-point number to an integral number before passing it to this formula.
Recursive Algorithm
So, to recursively extract all of the digits of a number of a certain length in order MSD->LSD, you can use the following Java method:
static public void extractDigits(int num, int length) {
if (length <= 0) { // base case
return;
}
else { // recursive case
int digit = (num % (int)Math.pow(10,length)) / (int)Math.pow(10,length-1);
/* do something with digit here */
extractDigits(num, length-1); // recurse
}
}
This method will never divide by zero.
Note: In order to "do something with digit here," you may need to pass in an additional parameter (e.g. if you want to add the digit to a list).
Optimization
Since your goal is to extract every digit from a number, rather than only one specific digit (as the basic formula assumes), this algorithm may be optimized to extract digits in order LSD->MSD so as to avoid the need for exponentiation at each step. (this approach original given here by #AdityaK ...please upvote them if you use it)
static public void extractDigits(int num) {
if (num == 0) { // base case
return;
}
else { // recursive case
int digit = num % 10;
/* do something with digit here */
extractDigits(num / 10); // recurse
}
}
Note: Any negative number should be converted to a positive number before passing it to this method.
Here's the code to recursively extract numbers from an integer. It will be in reverse order.
import java.util.*;
public class HelloWorld{
static void extractNumbers(int n, List<Integer> l) {
if(n==0)
return;
else {
l.add(n%10);
extractNumbers(n/10, l);
}
}
public static void main(String []args){
List<Integer> result = new ArrayList<Integer>();
extractNumbers(456789,result);
System.out.println(result);
}
}
Hope it helps.
I would do something like this:-
public static void main (String[] args) throws java.lang.Exception
{
// your code goes here
int num=23456;
int numSize=5;
rec(num,numSize);
}
public static void rec(int num, int numSize){
if(numSize==0)
return;
int divideBy=(int)Math.pow(10,(numSize-1));
int out=(int)(num/divideBy);
System.out.println(out);
rec((num-out*divideBy),(numSize-1));
return;
}
See the output from here: http://ideone.com/GR3l5d
This can be easily done by using the for loop by converting the array elements into string.
var arr = [234, 3456, 1234, 45679, 100];
var compare = function(val1, val2) {
return val1 - val2;
};
arr.sort(compare); //sort function
var extract = function(value, index) {
var j = "";
var element = value + "";
for (var i in element) {
var val = element[i];
console.log(parseInt(val)); // this prints the single digits from each array elements
j = j + " " + val;
}
alert(j);
};
arr.forEach(extract); //extract function..
Related
I am a beginner in Java and trying to learn. I have an integer from whom I want to calculate the double of each digit and then restore the answer in the integer. I think that I have to use the for() loop and tempvalue. I have the number 1234 and I need to get 2468.
I did this and I got 1234. Can someone find the issue, I am not very good with the index concept.
public class Doublevalue {
public static void main(String[] args) {
num=1234;
for(int i=0;num<0;i++) {
int tempvalue=(num%10*2)/10;
num=tempvalue;
System.out.print(num);
}}}
Because doubling digits is only valid when every digit is less than 5, the solution can be just
num *= 2;
But if you want the treat each digit separately, you need to do something like this:
int tmp = 0;
for (int column = 1; num > 0; column *= 10) {
tmp += (num % 10) * column * 2;
num /= 10;
}
num = tmp;
See live demo.
You can do an in-place replacement of each digit, but the logic is a little more complicated.
The code you currently provided has everything right - except for what you are doing in the loop.
In your example, you are executing int tempvalue=(num%10*2)/10;. I'm pretty certain that you are not sure what you are doing. What the line is doing is getting the remainder of the number when it is divided by 10, multiplying it by 2, then dividing by then. I can't seem to understand why you are doing this, so I will provide my own solution.
public class DoubleDigits {
public static void main(String[] args) {
DoubleDigits dd = new DoubleDigits();
System.out.println(dd.doubleDigits(1234));
}
public int doubleDigits(int number) {
StringBuilder str = new StringBuilder();
String testCase = String.valueOf(number);
for(int i = 0; i < testCase.length(); i++) {
int digit = Integer.parseInt(String.valueOf(testCase.charAt(i)))*2;
str.append(digit);
}
return Integer.parseInt(str.toString());
}
}
So what's happening?
First, we convert the number to a String, so we can get each single character (as a number). The for loop will loop through every single character, and we can use a StringBuilder to append the character after it has been parsed to an int and multiplied by two.
In the above example, the program produces:
2468
When the test case is:
1234
And when the test case is:
9999
The result is:
18181818
Hi I am making a method that can take an integer as a parameter and compute how many zeros its binary form has. So for example, if I have binaryZeros(44), its binary form is 101100. Therefore, binaryZeros(44) should return 3. However, I am making some errors and I cannot tell where it is coming from. I would appreciate it if someone can point out where I am making that error, or if my approach (logic) to this problem is good enough. Thank you!
My code is Below:
public static int binaryZeros(int n) {
int zeroCount = 0;
double m = n;
while (m >= 0.0) {
m = m / 2.0;
if (m == Math.floor(m)) {
zeroCount++;
} else {
m = Math.floor(m);
}
}
return zeroCount;
}
Below is a more concise way to solve this problem
public static int binaryZeros(int n) {
int zeroCount = 0;
// Run a while loop until n is greater than or equals to 1
while(n >= 1)
{
/* Use modulo operator to get the reminder of division by 2 (reminder will be 1 or 0 as you are dividing by 2).
Keep in mind that binary representation is an array of these reminders until the number is equal to 1.
And once the number is equal to 1 the reminder is 1, so you can exit the loop there.*/
if(n % 2 == 0)
{
zeroCount++;
}
n = n / 2;
}
return zeroCount;
}
Your approach is good, but I think there's a better way to do it. The Integer class has a static method that returns the binary of a number: Integer.toBinaryString(num) . This will return a String.
Then, you can just check if there are any 0 in that string with method that has a for loop and evaluating with an if:
public int getZeros(String binaryString){
int zeros = 0;
for(int i=0; i < binaryString.length; i++)
if(binaryString.charAt[i].equals('0')
zeros++;
return zeros;
}
I believe this would be a simpler option and it doesn't have any errors.
Once m == 0.0, it will never change, so your while loop will never stop.
If you start with a number m >= 0, it can never become negative no matter how many times you divide it by 2 or use Math.floor. The loop should stop when m reaches 0, so change the condition to while (m > 0.0).
Note that you could do the same thing with built-in standard library methods. For example, there is a method that returns the number of leading zeros in a number, and a method that returns the number of bits set to 1. Using both you can compute the number of zeros that are not leading zeros:
static int binaryZeros(int n) {
return Integer.SIZE - Integer.numberOfLeadingZeros(n) - Integer.bitCount(n);
}
Here is one way. It simply complements the integer reversing 1's and 0's and then counts the 1 bits. You should not be using floating point math when doing this.
~ complements the bits
&1 masks the low order bit. Is either 1 or 0
>>> shifts right 1 bit including sign bit.
System.out.println(binaryZeros(44) + " (" +Integer.toBinaryString(44) +")");
System.out.println(binaryZeros(-44) + " ("Integer.toBinaryString(-44)+")");
public static int binaryZeros(int v) {
int count = 0;
while (v != 0) {
// count 1 bits
// of ~v
count += (~v)&1;
v >>>=1;
}
return count;
}
Prints
3 (101100)
4 (11111111111111111111111111010100)
Just be simple, whe there's Integer.bitCount(n) method:
public static int binaryZeros(int n) {
long val = n & 0xFFFFFFFFL;
int totalBits = (int)(Math.log(val) / Math.log(2) + 1);
int setBits = Long.bitCount(val);
return totalBits - setBits;
}
public static int getZeros(int num) {
String str= Integer.toBinaryString(num);
int count=0;
for(int i=0; i<str.length(); i++) {
if(str.charAt(i)=='0') count++;
}
return count;
}
The method toBinaryString() returns a string representation of the integer argument as an unsigned integer in base 2. It accepts an argument in Int data-type and returns the corresponding binary string.
Then the for loop counts the number of zeros in the String and returns it.
I'm new to Java and had a question about summing together the digits of a single binary value in Java.
For example,
If the binary value has an even number of 1's, I would like to output the String "even" to another method. If there are an odd number of 1's, then I want to output the String value "odd".
Below is an example of my code:
String eoro;
String name = "1010101011";
int num = Integer.parseInt(name, 2);
System.out.println(num);
if(num % 2 == 0)
eoro = "even";
else
eoro = "odd";
System.out.println(eoro);
The output comes up as
683
odd
I'm not sure if Integer.parseInt(name, 2); is the correct way of doing this, but I am unaware of another way of summing the digits of a single String value.
Please do not be rude and thanks for any help you can provide!
The shortest would be probably:
new BigInteger(value, 2).bitCount();
new BigInteger(value, 2) parses string as binary integer, bitCount() counts the bits. I'd use BigInteger as it is not clear, how long the string might be. You could use Integer or Long or other types if you're sure the string is short enough.
Alternatively you can just cound 1s in the string.
int result = 0;
for (char c: value.toCharArray()) {
result += c == '1' ? 1 : 0;
}
Integer.parseInt is definitely not the right method. It will parse the given string to an integer, but an integer being odd or even is unrelated to the number of "1"s. E.g., consider the following:
public static void main(String[] args) {
String eoro;
String name = "10";
int num = Integer.parseInt(name, 2);
System.out.println(num);
if(num % 2 == 0)
eoro = "even";
else
eoro = "odd";
System.out.println(eoro);
}
This will print
2
even
Which is not the output you want.
An easy way to count 1s in a string is to stream its characters and count them:
long numOnes = name.chars().filter(c -> c == '1').count();
public static void main(String[] args) {
// declare variables
String name = "1010101011";
String eoro = (name.chars().filter(c -> c == '1').count() % 2 == 0)?"even":"odd";
System.out.print(eoro);
}
If the binary value has an even number of 1's, I would like to output the String "even"
Just because a binary value has an even number of 1's doesn't mean the decimal representation of that number be an even value, or num % 2 == 0. For example, if you have a 1 as the least significant value, as you have here, this will always make the value odd.
You can count using a loop, or like this.
int ones = name.replace("0", "").length();
if (ones % 2 == 0)
System.out.println("even");
else
System.out.println("odd");
Refer: Java: How do I count the number of occurrences of a char in a String?
Here is my challenge:
Given a list of non negative integers, arrange them in such a manner that they form the smallest number possible.
The result is going to be very large, hence return the result in the form of a string.
If I consider input array as {20, 1, 5} then all permutations are as below:
2015, 2051, 1205, 1520, 5201, 5120 but as 1205 is smallest hence it should be the result.
Input array {20, 1, 5}
Result: 1205
Here is the method signature:
private String getSmallestNumber(Integer[] nums) {
}
What algorithm should I use?
Similar type of question asked on:
http://www.practice.geeksforgeeks.org/problem-page.php?pid=380
I completed my code but please suggest me better algorithm
private String getSmallestNumber(Integer[] nums) {
String[] arr = new String[nums.length];
for (int i = 0; i < nums.length; i++) {
arr[i] = String.valueOf(nums[i]);
}
Arrays.sort(arr, new Comparator<String>() {
#Override
public int compare(String a, String b) {
return (a + b).compareTo(b + a);
}
});
StringBuilder sb = new StringBuilder();
for (String s : arr) {
sb.append(s);
}
while (sb.charAt(0) == '0' && sb.length() > 1) {
sb.deleteCharAt(0);
}
return sb.toString();
}
The solution is to sort the array using a custom comparator that compares digit-by-digit. In other words, given two numbers, compare the most-significant-digit of the first number to most-significant-digit of the second number. Then compare the second digits, and so on, until you reach the end of one of the numbers, or the digits aren't equal. The number with the lower digit goes first in the answer.
For example 20 comes before 5 because 2 is less than 5. 1000 comes before 99 because 1 is less than 9. 123789 comes before 1239 because 7 is less than 9.
So the trick is to scale the smaller number by multiplying by 10 until both numbers have the same number of digits. For example, given a six-digit number and a four-digit number like
123789
1239
you need to multiply the four-digit number by 100 so both numbers have the same number of digits
123789
123900
Then a simple integer comparison tells you that 123789 comes before 1239. So the code for the comparator looks like this
int compare( int a, int b )
{
int special = b - a; // special case, e.g. 123 and 123000
if ( a <= b ) {
for ( int n = 1; n <= b; n *= 10 )
if ( n > a )
a *= 10;
} else {
for ( int n = 1; n <= a; n *= 10 )
if ( n > b )
b *= 10;
}
if ( a == b )
return special;
else
return a - b;
}
There is a special case where the two numbers end up being equal after scaling. For example, given the numbers 123000 and 123, the correct order is to put 123000 before 123, since that puts the three zeros in the array first, i.e. 123000123 is better than 123123000. Hence a special case is needed to choose the larger number first, if the numbers are equal after scaling. Hence, the need for the variable called special.
I made a simple program that calculate the Mean and Median value of given array from command-line.
import java.util.Arrays;
public class EdankJaya {
public static void main(String args[]) {
double sum = 0;
double d;
if(args.length < 1) {
System.out.println("Usage : java EdankJaya <Number1> <Number2> ..");
System.exit(1);
}
//Mean
for(String s : args) {
d = Double.parseDouble(s);
sum = sum+d;
}
double mean = sum/args.length;
System.out.println("Mean: " + mean);
//Median
Arrays.sort(args);
int med = args.length/2;
if((args.length % 2) == 0) {
double median1 = Double.parseDouble(args[med-1]);
double median2 = Double.parseDouble(args[med]);
System.out.println("Median :"+(median1+median2)/2);
} else {
double median = Double.parseDouble(args[med]);
System.out.println("Median :"+median);
}
}
}
Technique that i used for Median value is divide args.length by 2 and store it in med. If args.length value is even, it'll be args[med-1] + args[med], no problem for even number. And for odd args.length value, it'll just be args[med], which is works fine on the paper since integer will not produce fraction(11/2 gonna be 5), but here's what happened:
Everything's good until i inputted 1-10, the value turned back to the result when i inputted 1-8, and 1-11 just like 1-7, and so on.
What could be the issue here.
Thanks.
Your array has strings in it, not numbers, so they are not sortting in numerical order. They're probably sorting in ASCII order. Since you're already iterating over the array and converting them to numbers, build a second array with them and sort that one.