Why does StringBuffer return a reference? - java

public class doubleSum {
private static String calculate(String a, String b){
String[] a_parts = a.split("\\.");
String[] b_parts = b.split("\\.");
StringBuffer sb = new StringBuffer();
int[] carrier = new int[]{0};
cal(a_parts[1],b_parts[1],sb, carrier);
sb.append(".");
cal(a_parts[0],b_parts[0],sb, carrier);
if(carrier[0] > 0)
sb.append(carrier);
return sb.reverse().toString();
}
private static void cal(String a, String b, StringBuffer sb, int[] carrier) {
int i = a.length() - 1;
int j = b.length() - 1;
while(i >= 0 || j >= 0) {
int sum = carrier[0];
if(i >= 0) {
sum += a.charAt(i) - '0';
i--;
}
if(j >= 0) {
sum += b.charAt(j) - '0';
j--;
}
carrier[0] = sum / 10;
sb.append(sum%10);
}
}
public static void main(String args[]) {
String res = calculate("6.91992", "4.10");
System.out.println(res);
}
}
I was trying to add two numbers with decimal point. However, when I print out, it was 6660f926#I[0.92002, something related to reference.
Anyone knows how to fix it?

You have a typo in your code. You appended the array itself, rather than the desired element of the array, so you've built yourself a String that literally contains the hashcode of your carrier array.
The line:
sb.append(carrier);
should be:
sb.append(carrier[0]);
Just FYI, what you believe to be a reference is actually the hashcode of the value of the field carrier.

Related

Randomize and shuffling a string without using stringbuilder or power tools

I want to shuffle a string without using any arrays, StringBuilder, or power tools (packages or methods that do the work for you) and using Math.random().
My code below works but I don't like it because I can't use string builder or .append(). Could someone help me and fix it?
public class loopPrr
{
static String shuffle(int a) {
String s = "BaaBooDaaDoo";
StringBuilder sb = new StringBuilder(a);
for (int i = 0; i < a; i++) {
int r = (int)(s.length() * Math.random());
sb.append(s.charAt(r));
}
return sb.toString();
}
}
If I got it right, you can simply use String:
static String shuffle(int a) {
String s = "BaaBooDaaDoo";
String sb = "";
for (int i = 0; i < a; i++) {
int r = (int) (s.length() * Math.random());
sb += s.charAt(r);
}
return sb;
}
I would suggest changing the name of "sb" variable to avoid misunderstanding though.
It is possible to shuffle a string by applying Fisher--Yates algorithm to the character array of the input string.
The algorithm basically consists in swapping the characters at randomized indexes as shown below.
static String shuffle(String str) {
char[] arr = str.toCharArray();
for (int i = str.length() - 1; i > 0 ; i--) { // starting from the last character
int x = (int)(i * Math.random()); // next index is in range [0...i-1]
char t = arr[i];
arr[i] = arr[x];
arr[x] = t;
}
return new String(arr);
}
If a randomized String of length a from the predefined alphabet needs to be generated, the following method can be implemented based on previous implementation for String to guarantee that all characters of the alphabet are used at least once if a >= alphabet.length:
private static final String LETTERS = "AaBbCcDdEe";
static String shuffle(int a) {
if (a <= 0) {
return "";
}
if (a < LETTERS.length()) {
char[] res = new char[a];
for (int i = 0, x = LETTERS.length(); x > 0 && i < a; i++, x--) {
res[i] = LETTERS.charAt((int)(Math.random() * x));
}
return new String(res);
}
return shuffle(shuffle(LETTERS) + shuffle(a - LETTERS.length()));
}

ArrayIndexOutOfBoundsException in ten's complement arithmetic implementation

My code tries to implement an algorithm to
take user input for two integer numbers and an operand + or - from the console,
store those numbers digit by digit in an int[50], representing negative ones in ten's complement format,
implement (decimal) digit-by-digit add/subtract operations,
print the result in decimal format without leading zeroes.
However, in my current implementation there are two problems
When adding 99 + 9999, the printed result is 01098 instead of the expected 010098.
When subtracting 99 - 9999, I get an ArrayIndexOutOfBoundsException: 50 instead of the expected result -09900.
import java.util.*;
public class Program9 {
public static String getOperand() {
Scanner scan = new Scanner(System.in);
String stringOfInteger;
System.out.print("Please enter an integer up to 50 numbers: ");
stringOfInteger = scan.nextLine();
return stringOfInteger;
}
public static int[] convert(String operand) {
int[] integer = new int[50];
char ch;
int position = operand.length() - 1;
for (int i = integer.length - 1; i >= 0; i--) {
if (position >= 0)
ch = operand.charAt(position--);
else
ch = 0;
if (ch >= '0' && ch <= '9') {
integer[i] = ch - '0';
} else {
integer[i] = 0;
}
}
return integer;
}
public static int[] add(int[] operand1, int[] operand2) {
int[] result = new int[operand1.length];
int carry = 0;
for (int i = operand1.length - 1; i >= 0; i--) {
result[i] = operand1[i] + operand2[i] + carry;
if (result[i] / 10 == 1) {
result[i] = result[i] % 10;
carry = 1;
} else
carry = 0;
}
return result;
}
public static int[] complement(int[] operand) {
int[] result = new int[operand.length];
for (int i = operand.length - 1; i >= 0; i--)
result[i] = 9 - operand[i];
return result;
}
public static int[] add1(int[] operand) {
int[] result = new int[50];
result[49] = 1;
for (int i = result.length - 2; i >= 0; i--)
result[i] = 0;
return result;
}
public static int[] negate(int[] operand) {
return add(add1(operand), complement(operand));
}
public static void print(int[] result, String operation) {
if (operation.charAt(0) == '+')
System.out.print("The subtotal of the two integer = ");
else if (operation.charAt(0) == '-')
System.out.print("The substraction of the two integers = ");
if (result[0] == 9) {
result = negate(result);
System.out.print("-");
for (int i = 0; i < result.length; i++) {
if (result[i] == 0 && result[i + 1] == 0)
continue;
else
System.out.print(result[i]);
}
} else
for (int i = 0; i < result.length; i++) {
if (result[i] == 0 && result[i + 1] == 0)
continue;
else
System.out.print(result[i]);
}
System.out.println();
}
public static void main(String[] args) {
Scanner scan = new Scanner(System.in);
int[] result = new int[50];
String string1 = getOperand();
String string2 = getOperand();
int[] integer1 = convert(string1);
int[] integer2 = convert(string2);
String operation;
System.out.print("Please enter which operation will be used (+ or -): ");
operation = scan.nextLine();
if (operation.charAt(0) == '+')
add(integer1, integer2);
else if (operation.charAt(0) == '-')
integer2 = negate(integer2);
result = add(integer1, integer2);
System.out.println(Arrays.toString(integer1));
System.out.println(Arrays.toString(integer2));
System.out.println(Arrays.toString(add(integer1, integer2)));
print(result, operation);
}
}
Okay, after so much discussion and so many issues with your code I have totally revised your original code because you said you wanted to learn more. Among other improvements I have done the following changes:
Meaninfgul class name
Meaningful method and parameter names
Convert repeated and often used constants like 50 and the array representation of the number 1 (needed for negation) into static final members for clean code reasons (documentation, easy change in one place, meaningful names), runtime optimisation).
Extend the code to permit negative integers as operands
Added validation patterns for user input. E.g. now the maximum number length is checked in order to avoid an array overflow.
Avoid numeric overflows during calculation by making the array bigger than the maximum number of digits permitted for user input (see source code comments)
Add retry loops with error handling for operand and operator input, extract console handling into one parametrised method.
Simplify code by removing unnecessary checks because user input is already validated before converting it into an int[].
Make debug output optional
package de.scrum_master.stackoverflow;
import java.util.Arrays;
import java.util.Scanner;
import java.util.regex.Pattern;
public class TensComplementArithmetic {
// Print debug messages?
private static final boolean DEBUG = true;
// Maximum length for numbers entered by a user
// (number of digits excluding the optional +/- sign)
private static final int MAX_NUMBER_LENGTH = 50;
// Array must have one additional element for the sign and
// one more to avoid overflows when adding big negative numbers
private static final int ARRAY_LENGTH = MAX_NUMBER_LENGTH + 2;
// Scanner for console input handling
private static final Scanner INPUT_SCANNER = new Scanner(System.in);
// Regex pattern for positive/negative integer number format verification incl. length check
private static final Pattern INTEGER_PATTERN = Pattern.compile("[+-]?[0-9]{1," + MAX_NUMBER_LENGTH + "}");
// Regex pattern for operator verification (currently only "+"/"-" allowed)
private static final Pattern OPERATOR_PATTERN = Pattern.compile("[+-]");
// The number 1 is always needed for converting a 9's into a 10's complement
// during negation, so we define it as a reusable constant
private static final int[] NUMBER_ONE;
static {
// Initialise constant carrying array representation for number 1
NUMBER_ONE = new int[ARRAY_LENGTH];
NUMBER_ONE[ARRAY_LENGTH - 1] = 1;
}
public static String readConsoleInput(String prompt, Pattern validationPattern, String errorMessage) {
String input = null;
while (input == null) {
System.out.print(prompt + ": ");
if (INPUT_SCANNER.hasNext(validationPattern))
input = INPUT_SCANNER.next(validationPattern);
else {
INPUT_SCANNER.nextLine();
System.out.println(errorMessage);
}
}
return input;
}
public static String getOperand(String operandName) {
return readConsoleInput(
"Operand " + operandName,
INTEGER_PATTERN,
"Illegal number format, please enter a positive/negative integer of max. " + MAX_NUMBER_LENGTH + " digits."
);
}
private static String getOperator() {
return readConsoleInput(
"Arithmetical operator (+ or -)",
OPERATOR_PATTERN,
"Unknown operator, try again."
);
}
public static int[] parseInteger(String number) {
char sign = number.charAt(0);
boolean isNegative = sign == '-' ? true : false;
if (isNegative || sign == '+')
number = number.substring(1);
int[] result = new int[ARRAY_LENGTH];
int parsePosition = number.length() - 1;
for (int i = result.length - 1; i >= 0; i--) {
if (parsePosition < 0)
break;
result[i] = number.charAt(parsePosition--) - '0';
}
return isNegative ? negate(result) : result;
}
public static int[] add(int[] operand1, int[] operand2) {
int[] result = new int[ARRAY_LENGTH];
int carry = 0;
for (int i = ARRAY_LENGTH - 1; i >= 0; i--) {
result[i] = operand1[i] + operand2[i] + carry;
if (result[i] >= 10) {
result[i] = result[i] % 10;
carry = 1;
} else
carry = 0;
}
return result;
}
public static int[] complement(int[] operand) {
int[] result = new int[ARRAY_LENGTH];
for (int i = operand.length - 1; i >= 0; i--)
result[i] = 9 - operand[i];
return result;
}
public static int[] negate(int[] operand) {
return add(complement(operand), NUMBER_ONE);
}
public static void print(int[] result, String operation) {
System.out.print(operation.charAt(0) == '-' ? "Difference = " : "Sum = ");
if (result[0] == 9) {
result = negate(result);
System.out.print("-");
}
boolean leadingZero = true;
for (int i = 0; i < result.length; i++) {
if (leadingZero) {
if (result[i] == 0)
continue;
leadingZero = false;
}
System.out.print(result[i]);
}
System.out.println(leadingZero ? "0" : "");
}
public static void main(String[] args) {
int[] operand1 = parseInteger(getOperand("#1"));
int[] operand2 = parseInteger(getOperand("#2"));
String operator = getOperator();
if (operator.equals("-"))
operand2 = negate(operand2);
int[] result = new int[ARRAY_LENGTH];
result = add(operand1, operand2);
if (DEBUG) {
System.out.println("Operand #1 = " + Arrays.toString(operand1));
System.out.println("Operand #2 = " + Arrays.toString(operand2));
System.out.println("Result = " + Arrays.toString(result));
}
print(result, operator);
}
}
Disclaimer: Your source code has multiple problems, but in order to keep it simple I am going to ignore most of them now and will just explain the reasons for your current problems and suggest fixes for them only.
If you check the array outputs from your main method, you see that the addition/subtraction results look good, i.e. the problem is not located in the calculation routines but in the print routine. There you have
duplicate code: The for loops printing the positive/negative numbers are identical.
a cosmetic problem: One leading zero is always printed.
a logical error: You check for two consecutive zeroes in order to determine where leading zeroes end and the actual number begins. But you forget that
within a number there can also be duplicate zeroes, e.g. within 10098 or -9900. This explains why 10098 is printed as 1098: You are suppressing the first zero from being printed.
if there is a zero in the last array element (e.g. 9900) you cannot check the (non-existent) subsequent element without causing an ArrayIndexOutOfBoundsException. This explains why you get the exception for -9900.
Now what can/should you do?
Eliminate the redundant for loop. You can use the same loop to print both positive and negative numbers.
Use a boolean flag in order to remember if you are still looping through leading zeroes or not.
You can change your print method like so:
public static void print(int[] result, String operation) {
System.out.print(operation.charAt(0) == '-' ? "Difference = " : "Sum = ");
if (result[0] == 9) {
result = negate(result);
System.out.print("-");
}
boolean leadingZero = true;
for (int i = 0; i < result.length; i++) {
if (leadingZero) {
if (result[i] == 0)
continue;
leadingZero = false;
}
System.out.print(result[i]);
}
System.out.println(leadingZero ? "0" : "");
}
The code after fixing the problems. all thanks to #kriegaex !
import java.util.*;
public class Program9 {
public static String getOperand() {
Scanner scan = new Scanner(System.in);
String stringOfInteger;
System.out.print("Please enter an integer up to 50 numbers: ");
stringOfInteger = scan.nextLine();
return stringOfInteger;
}
public static int[] convert(String operand) {
int [] integer = new int[50];
char ch;
int position = operand.length() - 1;
for (int i = integer.length - 1; i >= 0; i--) {
if (position >= 0)
ch = operand.charAt(position--);
else
ch = 0;
if (ch >= '0' && ch <= '9') {
integer[i] = ch - '0';
} else {
integer[i] = 0;
}
}
return integer;
}
public static int[] add(int[] operand1, int[] operand2) {
int [] result = new int[operand1.length];
int carry = 0;
for (int i = operand1.length - 1; i >= 0; i--) {
result[i] = operand1[i] + operand2[i] + carry;
if (result[i] / 10 == 1) {
result[i] = result[i] % 10;
carry = 1;
} else
carry = 0;
}
return result;
}
public static int[] complement(int[] operand2){
int [] result = new int[operand2.length];
for (int i = operand2.length - 1; i >= 0; i--)
result[i] = 9 - operand2[i];
return result;
}
public static int[] add1(int[] operand2){
int [] result = new int[operand2.length];
result[operand2.length - 1] = 1;
for (int i = result.length - 2; i >= 0; i--)
result[i] = 0;
return result;
}
public static int[] negate(int[] operand2){
return add(add1(operand2), complement(operand2));
}
public static void print(int[] result, String operation) {
if (operation.charAt(0) == '+')
System.out.print("The subtotal of the two integers = ");
else if (operation.charAt(0) == '-')
System.out.print("The subtraction of the two integers = ");
if (result[0] == 9) {
result = negate(result);
System.out.print("-");
}
boolean leadingZero = true;
for (int i = 0; i < result.length; i++) {
if (leadingZero) {
if (result[i] == 0)
continue;
leadingZero = false;
}
System.out.print(result[i]);
}
if (leadingZero == true)
System.out.println('0' - '0');
System.out.println();
}
public static void main(String[] args) {
Scanner scan = new Scanner(System.in);
int [] result = new int[50];
String string1 = getOperand();
String string2 = getOperand();
int [] integer1 = convert(string1);
int [] integer2 = convert(string2);
String operation;
System.out.print("Please enter which operation will be used (+ or -): ");
operation = scan.nextLine();
if (operation.charAt(0) == '+')
add(integer1, integer2);
else if (operation.charAt(0) == '-')
integer2 = negate(integer2);
result = add(integer1, integer2);
System.out.println(Arrays.toString(integer1));
System.out.println(Arrays.toString(integer2));
System.out.println(Arrays.toString(add(integer1, integer2)));
print(result, operation);
}
}

Searching LinkedList, comparing two "Strings"?

I have a LinkedList where each node contains a word. I also have a variable that contains 6 randomly generated letters. I have a code the determines all possible letter combinations of those letters. I need to traverse through the linked list and determine the best "match" among the nodes.
Example:
-Letters generated: jghoot
-Linked list contains: cat, dog, cow, loot, hooter, ghlooter (I know ghlooter isn't a word)
The method would return hooter because it shares the most characters and is most similar to it. Any ideas?
I guess you could say I am looking for the word that the generated letters are a substring of.
use a nested for loop, compare each letter of your original string with the one you are comparing it to, and for each match, increase a local int variable. at the end of the loop, compare local int variable to global int variable that holds the "best" match till that one, and if bigger, store local int into global one, and put your found node into global node. at the end you should have a node which matches closest.
something like this
int currBest = 0;
int currBestNode = firstNodeOfLinkedList;
while(blabla)
{
int localBest = 0;
for(i= 0; i < currentNodeWord.length; i++)
{
for(j=0; j < originalWord.length;j++)
{
if(currentNodeWord[i] == originalWord[j])
{
localBest++
}
}
}
if(localBest > currBest)
{
currBest = localBest;
currBestNode = currentNodeStringBeingSearched;
}
}
// here u are out of ur loop, ur currBestNode should be set to the best match found.
hope that helps
If you're considering only character counts, first you need a method to count chars in a word
public int [] getCharCounts(String word) {
int [] result = new int['z' - 'a' + 1];
for(int i = 0; i<word.length(); i++) result[word.charAt(i) - 'a']++;
return result;
}
and then you need to compare character counts of two words
public static int compareCounts(int [] count1, int [] count2) [
int result = 0;
for(int i = 0; i<count1.length; i++) {
result += Math.min(count1[i], count2[i]);
}
return result;
}
public static void main(String[] args) {
String randomWord = "jghoot";
int [] randomWordCharCount = getCharCounts(randomWord);
ArrayList<String> wordList = new ArrayList();
String bestElement = null;
int bestMatch = -1;
for(String word : wordList) {
int [] wordCount = getCharCounts(word);
int cmp = compareCounts(randomWordCharCount, wordCount);
if(cmp > bestMatch) {
bestMatch = cmp;
bestElement = word;
}
}
System.out.println(word);
}
I think this works.
import java.util.*;
import java.io.*;
class LCSLength
{
public static void main(String args[])
{
ArrayList<String> strlist=new ArrayList<String>();
strlist.add(new String("cat"));
strlist.add(new String("cow"));
strlist.add(new String("hooter"));
strlist.add(new String("dog"));
strlist.add(new String("loot"));
String random=new String("jghoot"); //Your String
int maxLength=-1;
String maxString=new String();
for(String s:strlist)
{
int localMax=longestSubstr(s,random);
if(localMax>maxLength)
{
maxLength=localMax;
maxString=s;
}
}
System.out.println(maxString);
}
public static int longestSubstr(String first, String second) {
if (first == null || second == null || first.length() == 0 || second.length() == 0) {
return 0;
}
int maxLen = 0;
int fl = first.length();
int sl = second.length();
int[][] table = new int[fl+1][sl+1];
for(int s=0; s <= sl; s++)
table[0][s] = 0;
for(int f=0; f <= fl; f++)
table[f][0] = 0;
for (int i = 1; i <= fl; i++) {
for (int j = 1; j <= sl; j++) {
if (first.charAt(i-1) == second.charAt(j-1)) {
if (i == 1 || j == 1) {
table[i][j] = 1;
}
else {
table[i][j] = table[i - 1][j - 1] + 1;
}
if (table[i][j] > maxLen) {
maxLen = table[i][j];
}
}
}
}
return maxLen;
}
}
Credits: Wikipedia for longest common substring algorithm.
http://en.wikibooks.org/wiki/Algorithm_Implementation/Strings/Longest_common_substring

Manually converting a string to an integer in Java

I'm having string consisting of a sequence of digits (e.g. "1234"). How to return the String as an int without using Java's library functions like Integer.parseInt?
public class StringToInteger {
public static void main(String [] args){
int i = myStringToInteger("123");
System.out.println("String decoded to number " + i);
}
public int myStringToInteger(String str){
/* ... */
}
}
And what is wrong with this?
int i = Integer.parseInt(str);
EDIT :
If you really need to do the conversion by hand, try this:
public static int myStringToInteger(String str) {
int answer = 0, factor = 1;
for (int i = str.length()-1; i >= 0; i--) {
answer += (str.charAt(i) - '0') * factor;
factor *= 10;
}
return answer;
}
The above will work fine for positive integers, if the number is negative you'll have to do a little checking first, but I'll leave that as an exercise for the reader.
If the standard libraries are disallowed, there are many approaches to solving this problem. One way to think about this is as a recursive function:
If n is less than 10, just convert it to the one-character string holding its digit. For example, 3 becomes "3".
If n is greater than 10, then use division and modulus to get the last digit of n and the number formed by excluding the last digit. Recursively get a string for the first digits, then append the appropriate character for the last digit. For example, if n is 137, you'd recursively compute "13" and tack on "7" to get "137".
You will need logic to special-case 0 and negative numbers, but otherwise this can be done fairly simply.
Since I suspect that this may be homework (and know for a fact that at some schools it is), I'll leave the actual conversion as an exercise to the reader. :-)
Hope this helps!
Use long instead of int in this case.
You need to check for overflows.
public static int StringtoNumber(String s) throws Exception{
if (s == null || s.length() == 0)
return 0;
while(s.charAt(0) == ' '){
s = s.substring(1);
}
boolean isNegative = s.charAt(0) == '-';
if (s.charAt(0) == '-' || (s.charAt(0) == '+')){
s = s.substring(1);
}
long result = 0l;
for (int i = 0; i < s.length(); i++){
int value = s.charAt(i) - '0';
if (value >= 0 && value <= 9){
if (!isNegative && 10 * result + value > Integer.MAX_VALUE ){
throw new Exception();
}else if (isNegative && -1 * 10 * result - value < Integer.MIN_VALUE){
throw new Exception();
}
result = 10 * result + value;
}else if (s.charAt(i) != ' '){
return (int)result;
}
}
return isNegative ? -1 * (int)result : (int)result;
}
Alternate approach to the answer already posted here. You can traverse the string from the front and build the number
public static void stringtoint(String s){
boolean isNegative=false;
int number =0;
if (s.charAt(0)=='-') {
isNegative=true;
}else{
number = number* 10 + s.charAt(0)-'0';
}
for (int i = 1; i < s.length(); i++) {
number = number*10 + s.charAt(i)-'0';
}
if(isNegative){
number = 0-number;
}
System.out.println(number);
}
Given the right hint, I think most people with a high school education can solve this own their own. Every one knows 134 = 100x1 + 10x3 + 1x4
The key part most people miss, is that if you do something like this in Java
System.out.println('0'*1);//48
it will pick the decimal representation of character 0 in ascii chart and multiply it by 1.
In ascii table character 0 has a decimal representation of 48. So the above line will print 48. So if you do something like '1'-'0' That is same as 49-48. Since in ascii chart, characters 0-9 are continuous, so you can take any char from 0 to 9 and subtract 0 to get its integer value. Once you have the integer value for a character, then converting the whole string to int is straight forward.
Here is another one solution to the problem
String a = "-12512";
char[] chars = a.toCharArray();
boolean isNegative = (chars[0] == '-');
if (isNegative) {
chars[0] = '0';
}
int multiplier = 1;
int total = 0;
for (int i = chars.length - 1; i >= 0; i--) {
total = total + ((chars[i] - '0') * multiplier);
multiplier = multiplier * 10;
}
if (isNegative) {
total = total * -1;
}
Use this:
static int parseInt(String str) {
char[] ch = str.trim().toCharArray();
int len = ch.length;
int value = 0;
for (int i=0, j=(len-1); i<len; i++,j--) {
int c = ch[i];
if (c < 48 || c > 57) {
throw new NumberFormatException("Not a number: "+str);
}
int n = c - 48;
n *= Math.pow(10, j);
value += n;
}
return value;
}
And by the way, you can handle the special case of negative integers, otherwise it will throw exception NumberFormatException.
You can do like this: from the string, create an array of characters for each element, keep the index saved, and multiply its ASCII value by the power of the actual reverse index. Sum the partial factors and you get it.
There is only a small cast to use Math.pow (since it returns a double), but you can avoid it by creating your own power function.
public static int StringToInt(String str){
int res = 0;
char [] chars = str.toCharArray();
System.out.println(str.length());
for (int i = str.length()-1, j=0; i>=0; i--, j++){
int temp = chars[j]-48;
int power = (int) Math.pow(10, i);
res += temp*power;
System.out.println(res);
}
return res;
}
Using Java 8 you can do the following:
public static int convert(String strNum)
{
int result =strNum.chars().reduce(0, (a, b)->10*a +b-'0');
}
Convert srtNum to char
for each char (represented as 'b') -> 'b' -'0' will give the relative number
sum all in a (initial value is 0)
(each time we perform an opertaion on a char do -> a=a*10
Make use of the fact that Java uses char and int in the same way. Basically, do char - '0' to get the int value of the char.
public class StringToInteger {
public static void main(String[] args) {
int i = myStringToInteger("123");
System.out.println("String decoded to number " + i);
}
public static int myStringToInteger(String str) {
int sum = 0;
char[] array = str.toCharArray();
int j = 0;
for(int i = str.length() - 1 ; i >= 0 ; i--){
sum += Math.pow(10, j)*(array[i]-'0');
j++;
}
return sum;
}
}
public int myStringToInteger(String str) throws NumberFormatException
{
int decimalRadix = 10; //10 is the radix of the decimal system
if (str == null) {
throw new NumberFormatException("null");
}
int finalResult = 0;
boolean isNegative = false;
int index = 0, strLength = str.length();
if (strLength > 0) {
if (str.charAt(0) == '-') {
isNegative = true;
index++;
}
while (index < strLength) {
if((Character.digit(str.charAt(index), decimalRadix)) != -1){
finalResult *= decimalRadix;
finalResult += (str.charAt(index) - '0');
} else throw new NumberFormatException("for input string " + str);
index++;
}
} else {
throw new NumberFormatException("Empty numeric string");
}
if(isNegative){
if(index > 1)
return -finalResult;
else
throw new NumberFormatException("Only got -");
}
return finalResult;
}
Outcome:
1) For the input "34567" the final result would be: 34567
2) For the input "-4567" the final result would be: -4567
3) For the input "-" the final result would be: java.lang.NumberFormatException: Only got -
4) For the input "12ab45" the final result would be: java.lang.NumberFormatException: for input string 12ab45
public static int convertToInt(String input){
char[] ch=input.toCharArray();
int result=0;
for(char c : ch){
result=(result*10)+((int)c-(int)'0');
}
return result;
}
Maybe this way will be a little bit faster:
public static int convertStringToInt(String num) {
int result = 0;
for (char c: num.toCharArray()) {
c -= 48;
if (c <= 9) {
result = (result << 3) + (result << 1) + c;
} else return -1;
}
return result;
}
This is the Complete program with all conditions positive, negative without using library
import java.util.Scanner;
public class StringToInt {
public static void main(String args[]) {
String inputString;
Scanner s = new Scanner(System.in);
inputString = s.nextLine();
if (!inputString.matches("([+-]?([0-9]*[.])?[0-9]+)")) {
System.out.println("error!!!");
} else {
Double result2 = getNumber(inputString);
System.out.println("result = " + result2);
}
}
public static Double getNumber(String number) {
Double result = 0.0;
Double beforeDecimal = 0.0;
Double afterDecimal = 0.0;
Double afterDecimalCount = 0.0;
int signBit = 1;
boolean flag = false;
int count = number.length();
if (number.charAt(0) == '-') {
signBit = -1;
flag = true;
} else if (number.charAt(0) == '+') {
flag = true;
}
for (int i = 0; i < count; i++) {
if (flag && i == 0) {
continue;
}
if (afterDecimalCount == 0.0) {
if (number.charAt(i) - '.' == 0) {
afterDecimalCount++;
} else {
beforeDecimal = beforeDecimal * 10 + (number.charAt(i) - '0');
}
} else {
afterDecimal = afterDecimal * 10 + number.charAt(i) - ('0');
afterDecimalCount = afterDecimalCount * 10;
}
}
if (afterDecimalCount != 0.0) {
afterDecimal = afterDecimal / afterDecimalCount;
result = beforeDecimal + afterDecimal;
} else {
result = beforeDecimal;
}
return result * signBit;
}
}
Works for Positive and Negative String Using TDD
//Solution
public int convert(String string) {
int number = 0;
boolean isNegative = false;
int i = 0;
if (string.charAt(0) == '-') {
isNegative = true;
i++;
}
for (int j = i; j < string.length(); j++) {
int value = string.charAt(j) - '0';
number *= 10;
number += value;
}
if (isNegative) {
number = -number;
}
return number;
}
//Testcases
public class StringtoIntTest {
private StringtoInt stringtoInt;
#Before
public void setUp() throws Exception {
stringtoInt = new StringtoInt();
}
#Test
public void testStringtoInt() {
int excepted = stringtoInt.convert("123456");
assertEquals(123456,excepted);
}
#Test
public void testStringtoIntWithNegative() {
int excepted = stringtoInt.convert("-123456");
assertEquals(-123456,excepted);
}
}
//Take one positive or negative number
String str="-90997865";
//Conver String into Character Array
char arr[]=str.toCharArray();
int no=0,asci=0,res=0;
for(int i=0;i<arr.length;i++)
{
//If First Character == negative then skip iteration and i++
if(arr[i]=='-' && i==0)
{
i++;
}
asci=(int)arr[i]; //Find Ascii value of each Character
no=asci-48; //Now Substract the Ascii value of 0 i.e 48 from asci
res=res*10+no; //Conversion for final number
}
//If first Character is negative then result also negative
if(arr[0]=='-')
{
res=-res;
}
System.out.println(res);
public class ConvertInteger {
public static int convertToInt(String numString){
int answer = 0, factor = 1;
for (int i = numString.length()-1; i >= 0; i--) {
answer += (numString.charAt(i) - '0') *factor;
factor *=10;
}
return answer;
}
public static void main(String[] args) {
System.out.println(convertToInt("789"));
}
}

Permutate a String to upper and lower case

I have a string, "abc". How would a program look like (if possible, in Java) who permute the String?
For example:
abc
ABC
Abc
aBc
abC
ABc
abC
AbC
Something like this should do the trick:
void printPermutations(String text) {
char[] chars = text.toCharArray();
for (int i = 0, n = (int) Math.pow(2, chars.length); i < n; i++) {
char[] permutation = new char[chars.length];
for (int j =0; j < chars.length; j++) {
permutation[j] = (isBitSet(i, j)) ? Character.toUpperCase(chars[j]) : chars[j];
}
System.out.println(permutation);
}
}
boolean isBitSet(int n, int offset) {
return (n >> offset & 1) != 0;
}
As you probably already know, the number of possible different combinations is 2^n, where n equals the length of the input string.
Since n could theoretically be fairly large, there's a chance that 2^n will exceed the capacity of a primitive type such as an int. (The user may have to wait a few years for all of the combinations to finish printing, but that's their business.)
Instead, let's use a bit vector to hold all of the possible combinations. We'll set the number of bits equal to n and initialize them all to 1. For example, if the input string is "abcdefghij", the initial bit vector values will be {1111111111}.
For every combination, we simply have to loop through all of the characters in the input string and set each one to uppercase if its corresponding bit is a 1, else set it to lowercase. We then decrement the bit vector and repeat.
For example, the process would look like this for an input of "abc":
Bits:   Corresponding Combo:
111    ABC
110    ABc
101    AbC
100    Abc
011    aBC
010    aBc
001    abC
000    abc
By using a loop rather than a recursive function call, we also avoid the possibility of a stack overflow exception occurring on large input strings.
Here is the actual implementation:
import java.util.BitSet;
public void PrintCombinations(String input) {
char[] currentCombo = input.toCharArray();
// Create a bit vector the same length as the input, and set all of the bits to 1
BitSet bv = new BitSet(input.length());
bv.set(0, currentCombo.length);
// While the bit vector still has some bits set
while(!bv.isEmpty()) {
// Loop through the array of characters and set each one to uppercase or lowercase,
// depending on whether its corresponding bit is set
for(int i = 0; i < currentCombo.length; ++i) {
if(bv.get(i)) // If the bit is set
currentCombo[i] = Character.toUpperCase(currentCombo[i]);
else
currentCombo[i] = Character.toLowerCase(currentCombo[i]);
}
// Print the current combination
System.out.println(currentCombo);
// Decrement the bit vector
DecrementBitVector(bv, currentCombo.length);
}
// Now the bit vector contains all zeroes, which corresponds to all of the letters being lowercase.
// Simply print the input as lowercase for the final combination
System.out.println(input.toLowerCase());
}
public void DecrementBitVector(BitSet bv, int numberOfBits) {
int currentBit = numberOfBits - 1;
while(currentBit >= 0) {
bv.flip(currentBit);
// If the bit became a 0 when we flipped it, then we're done.
// Otherwise we have to continue flipping bits
if(!bv.get(currentBit))
break;
currentBit--;
}
}
String str = "Abc";
str = str.toLowerCase();
int numOfCombos = 1 << str.length();
for (int i = 0; i < numOfCombos; i++) {
char[] combinations = str.toCharArray();
for (int j = 0; j < str.length(); j++) {
if (((i >> j) & 1) == 1 ) {
combinations[j] = Character.toUpperCase(str.charAt(j));
}
}
System.out.println(new String(combinations));
}
You can also use backtracking to solve this problem:
public List<String> letterCasePermutation(String S) {
List<String> result = new ArrayList<>();
backtrack(0 , S, "", result);
return result;
}
private void backtrack(int start, String s, String temp, List<String> result) {
if(start >= s.length()) {
result.add(temp);
return;
}
char c = s.charAt(start);
if(!Character.isAlphabetic(c)) {
backtrack(start + 1, s, temp + c, result);
return;
}
if(Character.isUpperCase(c)) {
backtrack(start + 1, s, temp + c, result);
c = Character.toLowerCase(c);
backtrack(start + 1, s, temp + c, result);
}
else {
backtrack(start + 1, s, temp + c, result);
c = Character.toUpperCase(c);
backtrack(start + 1, s, temp + c, result);
}
}
Please find here the code snippet for the above :
public class StringPerm {
public static void main(String[] args) {
String str = "abc";
String[] f = permute(str);
for (int x = 0; x < f.length; x++) {
System.out.println(f[x]);
}
}
public static String[] permute(String str) {
String low = str.toLowerCase();
String up = str.toUpperCase();
char[] l = low.toCharArray();
char u[] = up.toCharArray();
String[] f = new String[10];
f[0] = low;
f[1] = up;
int k = 2;
char[] temp = new char[low.length()];
for (int i = 0; i < l.length; i++)
{
temp[i] = l[i];
for (int j = 0; j < u.length; j++)
{
if (i != j) {
temp[j] = u[j];
}
}
f[k] = new String(temp);
k++;
}
for (int i = 0; i < u.length; i++)
{
temp[i] = u[i];
for (int j = 0; j < l.length; j++)
{
if (i != j) {
temp[j] = l[j];
}
}
f[k] = new String(temp);
k++;
}
return f;
}
}
You can do something like
```
import java.util.*;
public class MyClass {
public static void main(String args[]) {
String n=(args[0]);
HashSet<String>rs = new HashSet();
helper(rs,n,0,n.length()-1);
System.out.println(rs);
}
public static void helper(HashSet<String>rs,String res , int l, int n)
{
if(l>n)
return;
for(int i=l;i<=n;i++)
{
res=swap(res,i);
rs.add(res);
helper(rs,res,l+1,n);
res=swap(res,i);
}
}
public static String swap(String st,int i)
{
char c = st.charAt(i);
char ch[]=st.toCharArray();
if(Character.isUpperCase(c))
{
c=Character.toLowerCase(c);
}
else if(Character.isLowerCase(c))
{
c=Character.toUpperCase(c);
}
ch[i]=c;
return new String(ch);
}
}
```

Categories

Resources