Check input string to int - java

I have this method:
public static int parseInt(String str) {
if (isValidNumber(str)) {
int sum = 0;
int position = 1;
for (int i = str.length() - 1; i >= 0; i--) {
int number = str.charAt(i) - '0';
sum += number * position;
position = position * 10;
}
return sum;
}
return -1;
}
which converts a string into a integer. And as you can see it is (at the moment) in a if-statement with a method which checks if the input is a valid input for my purpose:
public static boolean isValidNumber(String str) {
for (int i = 0; i < str.length(); i++) {
char c = str.charAt(i);
if(c >= '0' && c <= '9'){
return true;
}
}
return false;
}
I want the string to be number only (negative and positive) no other is allowed. At that time a string i.e 1a1a will be converted to a integer which it shouldn't whereas -1 will not be converted. I think you guys understand what I mean. I don't know how to do that.
Please help!

Try this:
CODE:
public class validNumbers {
public static void main(String[] args) {
System.out.println(parseInt("345"));
System.out.println(parseInt("-345"));
System.out.println(parseInt("a-345"));
System.out.println(parseInt("1a5b"));
}
public static int parseInt(String str) {
String numberWithoutSign = removeSign(str);
if (isValidNumber(numberWithoutSign)) {
int sum = 0;
int position = 1;
for (int i = numberWithoutSign.length() - 1; i >= 0; i--) {
int number = numberWithoutSign.charAt(i) - '0';
sum += number * position;
position = position * 10;
}
if(isNegative(str)){
return -(sum);
}else{
return sum;
}
}
return -1;
}
/**
* Removes sign in number if exists
*/
public static String removeSign(String number){
if(number.charAt(0) == '+' || number.charAt(0) == '-'){
return number.substring(1);
}else{
return number;
}
}
/**
* Determines if a number is valid
*/
public static boolean isValidNumber(String number) {
for (int i = 0; i < number.length(); i++) {
char c = number.charAt(i);
if(c >= '0' && c <= '9'){
continue;
}else{
return false;
}
}
return true;
}
/**
* Determines if a number is negative or not
*/
public static boolean isNegative(String number){
if(number.charAt(0) == '-'){
return true;
}else{
return false;
}
}
}
OUTPUT:
345
-345
-1
-1

To check if a string is a real number you can use a method like this:
public static boolean isInteger(String str) {
try {
Integer.parseInt(str);
return true;
} catch (NumberFormatException nfe) {}
return false;
}

The problem is with your function isValidNumber. It should return a false on first occurrence of a non numeric value, as follows:
public static boolean isValidNumber(String str) {
for (int i = 0; i < str.length(); i++) {
char c = str.charAt(i);
if(!(c >= '0' && c <= '9')){
if (i > 0) {
return false;
}
//This will only be invoked when `i == 0` (or less, which is impossible in this for loop), so I don't need to explicitly specify it here, as I have checked for `i > 0` in the above code...
if (c != '-' && c != '+') {
return false;
}
}
}
return true;
}

Related

What am I doing wrong in this loop?

So for I am trying to make a boolean method that checks if an inputed string is a positive integer. It will return true if it is a positive integer and false if it is anything else. Here is my code:
public static boolean isPositiveInteger(String input) {
int stringLength = input.length();
int index = stringLength-1;
while(index>0) {
index--;
if(input.charAt(0) != '-' && input.charAt(index) >= '0' &&
input.charAt(index) <= '9') {
return true;
}
return false;
}
return false;
}
When the input is the string "fish33" the method will return true instead of false. Why is that?
Your while loop executes only once - return will stop execution. Moreover, you start with second to last, not with last character. Replace your code with this one:
public static boolean isPositiveInteger(String input) {
int stringLength = input.length();
int index = stringLength;
// special case when input is empty string
if (index == 0) {
return false;
}
while(index > 0) {
index--;
// if some of the characters is not digit, return false
if !(input.charAt(index) >= '0' &&
input.charAt(index) <= '9') {
return false;
}
}
// if the while loop does not find any other character, return true
return true;
}
There is no point to make so many manipulations, it can be solved in few lines
public static void main(String[] args) {
System.out.println(isPositiveInteger("1"));
System.out.println(isPositiveInteger("abc"));
}
public static boolean isPositiveInteger(String input) {
try {
Integer i = Integer.parseInt(input);
return i > 0;
}
catch(NumberFormatException nfe){
return false;
}
}

Making method to give value of m or M based on position

So i have to make a method that will return a value based on m or M in a string. so far i have this
public static int mIndex(String x) {
if (x.indexOf('M') >= 0) {
return x.indexOf('M');
}
if (x.indexOf('m') >= 0) {
return x.indexOf('m');
} else {
return -1;
}
}
The problem is that it only returns M if it is first in the String. Is there anyway for it to detect m or M, and then give a value based on that?
For something like that, a regular expression is your friend:
public static int mIndex(String x) {
Matcher m = Pattern.compile("[mM]").matcher(x);
if (m.find())
return m.start();
return -1;
}
Test
System.out.println(mIndex("kamdkMMM"));
System.out.println(mIndex("KAMDKmmm"));
System.out.println(mIndex("Hello World"));
Output
2
2
-1
Try this:
String s = "MarshmallowmmMaM";
System.out.println("Index of 'M':");
int index = s.indexOf("M");
while (index >= 0) {
System.out.println(index);
index = s.indexOf("M", index + 1);
}
System.out.println("Index of 'm':");
index = s.indexOf("m");
while (index >= 0) {
System.out.println(index);
index = s.indexOf("m", index + 1);
}
Output:
Index of 'M':
0
13
15
Index of 'm':
5
11
12
If you want to detect the first position of each case for letter M. "upper&lower".
public class Main {
public static int M_POSITION = -1;
public static int m_POSITION = -1;
public static void mIndex(String x) {
int i = 0;
while (i < x.length()) {
if (x.charAt(i) == 'M') {
if (M_POSITION == -1)
M_POSITION = i;
} else if (x.charAt(i) == 'm') {
if (m_POSITION == -1)
m_POSITION = i;
}
++i;
}
}
public static void main(String[] args) {
mIndex("adsm");
System.out.println(m_POSITION);
System.out.println(M_POSITION);
}
}

Return the sum of all integers from a random String without using regex

I was asked this question in an interview recently (Java programming que)
Return the sum of all integers from a random String.
Just iterate over the string, handle one digit at a time. This is pretty much exactly what the regex would do anyway:
String testStrings[] = { "-1a2b3c", "123ab!45c", "abcdef", "0123.4",
"dFD$#23+++12##T1234;/.,10" };
for (String testString : testStrings) {
String currentNumber = "";
int sum = 0;
for (int i = 0; i < testString.length(); i++) {
char currentChar = testString.charAt(i);
// Add digits or a leading minus to "currentNumber"
if (Character.isDigit(currentChar)
|| (currentNumber.equals("") && currentChar == '-')) {
currentNumber += currentChar;
} else {
// We've stumbled across a non-digit char.
//Try to parse the "currentNumber" we have so far
if (!currentNumber.equals("") && !currentNumber.equals("-"))
sum += Integer.parseInt(currentNumber);
currentNumber = "";
}
}
// Add the last "currentNumber" in case the string ends with a
// number
if (!currentNumber.equals("") && !currentNumber.equals("-"))
sum += Integer.parseInt(currentNumber);
System.out.println(sum);
}
Output:
4
168
0
127
1279
public class Random {
public int SumofNumbers(String s){
char[] str = s.toCharArray();
String answer="";
int sum = 0;
List<String> al = new ArrayList();
for (int i=0;i< str.length;i++){
if (checkNumber(str[i])){
answer=answer+str[i];
}
else
{
if(!answer.isEmpty()){
al.add(answer);
answer = "";
}
}
if (i == str.length -1 && !answer.isEmpty()) {
al.add(answer);
}
}
for (String a1 : al){
sum = sum + Integer.valueOf(a1);
}
return sum;
}
private boolean checkNumber(char c) {
if ((int)c > 47 && (int)c < 58){
return true;
}else if ((int)c == 45){
return true;
}
return false;
}
public static void main(String [] args){
Random r = new Random();
String test = "123ab!45c";
System.out.println(r.SumofNumbers(test));
}
}
public class StringToIntAddition {
public static void main(String[] args) throws Exception {
String str = "2e40 ssdf 23-9", number="";
int sum=0;
for(int i=0; i<str.length() ;i++){
if(Character.isDigit(str.charAt(i))){
number += str.charAt(i);
}
else if(!number.isEmpty()){
sum += Integer.parseInt(number);
number= "";
}
if (str.charAt(i) == '-'){
number = "-" ;
}
}
if(!number.isEmpty()){
sum += Integer.parseInt(number);
}
System.out.println("number= " + sum);
}
}
I've got a slightly 'cute' way to do this in Java 8: implement it as a Collector
public DigitCollector {
private boolean negative = false;
private int current = 0;
private int total = 0;
public int getTotal() {
if (negative) {
total -= current;
} else {
total += current;
}
current = 0;
negative = false;
return total;
}
public void accept(Character ch) {
if (Character.isDigit(ch)) {
current = 10 * current + Integer.parseInt(ch.toString());
} else if (ch.equals('-')) {
negative = true;
} else {
getTotal();
}
}
}
Now you can collect a stream of characters:
text.chars().map(ch -> new Character((char)ch))
.collect(DigitCollector::new, DigitCollector::accept, null)
.getTotal();
I realise the mapping ch -> new Character((char)ch)) looks strange but .chars() returns a stream of integers instead of characters. See here for reasons why (though pretty much everyone agrees it was a mistake).
This is a slightly longwinded way of doing it but it's pretty flexible: you could take a stream of Character from anywhere and do any sort of manipulation you wanted before collecting them. It seems to me to be a natural representation of the problem and, mostly, I just reckon streams are cooler than traditional iteration :-)
There's already quite a few answers, but this one seemed fun. I have a different solution that should be pretty efficient:
public static int countString(String input) {
if (input == null) return 0;
int sum = 0;
int accumulator = 0;
boolean lastCharWasDigit = false;
for (int i = 0, len = input.length(); ++i) {
char c = input.charAt(i);
// If a non-digit character is found, clear the
// accumulator and add it to the sum.
if (c < '0' || c > '9') {
sum += accumulator;
accumulator = 0;
lastCharWasDigit = false;
continue;
}
// If the previous character was a digit, that means
// this is a continuation. Multiply by ten to shift
// it over one power of ten before adding the new value
if (lastCharWasDigit) {
accumulator *= 10;
}
// Add the integer value of the character
int charValue = c - '0';
accumulator += charValue;
lastCharWasDigit = true;
}
// Finally, clear the accumulator for any ending digits,
// and return the sum
sum += accumulator;
return sum;
}

recursive factorial formula

I want to get an output that displays something like 1*2*3*4 but instead I get 4*3*2*1
this is my code:
public static int fact(int n)
{
if(n ==1)
return 1;
else
return n * fact(n-1);
}
public static int factorForm(int n)
{
System.out.print(n);
if (n == 1)
return 1;
else
{
System.out.print("*");
return n + '*' + factorForm(n-1);
}
}
You are calling fact(4)
Then you print
Then you call fact(3)
If you invert that you'll get what you want:
public class fact {
static int f(int n)
{
if (n ==1 )
{
System.out.print(1);
return 1;
}
int ret= (n * f(n-1));
System.out.print("*");
System.out.print(n);
return ret;
}
public static void main(String[] args)
{
int ret=f(4);
System.out.print("=");
System.out.println(ret);
}
}
To reverse the output, n should be printed after making the recursive call:
public static int factorForm(int n)
{
if (n == 1)
{
System.out.print(1);
return 1;
}
else
{
int rest = factorForm(n-1); // prints 1*2*...*n-1
System.out.print("*");
System.out.print(n);
return rest * n;
}
}
The expression n + '*' + factorForm(n-1) performs integer addition, not multiplication or string concatenation. I changed it to perform multiplication. If the intention is to return the string that was printed, the return type and the type of rest should be changed to String, the return value in the base case should be "1", and that expression should be changed to rest + "*" + n.
Return after printing as below, more importantly understand how recursion works:
public static int factorForm(int n)
{
if (n == 1){
System.out.print("1*");
return 1;
}
else
{
int val = n * factorForm(n-1);
System.out.print(n + "*");
return val;
}
}
if you want to get like 1*2*3*4 result. i think you can do this.
this is my code:
public static String fact(int n) {
if (n < 1) {
throw new RuntimeException("n must be int type and up 0");
}
else if (n == 1) {
return "1";
} else {
return n + "*" + fact(n - 1);
}
}
public static String factorForm(String str) {
String [] arr = str.split("\\*");
String [] newArr = new String[arr.length];
String result = "";
if (arr.length > 1) {
for (int i = 0; i < arr.length; i++) {
newArr[arr.length - i - 1] = arr[i];
}
for (int i = 0; i < newArr.length; i++) {
result += newArr[i] + (i != newArr.length - 1 ? "*" : "");
}
return result;
} else {
return str;
}
}
like this. you can get results what you get. may be complicated.

Java: Implement String method contains() without built-in method contains()

I'm trying to implement String method contains() without using the built-in contains() method.
Here is what I have so far:
public static boolean containsCS(String str, CharSequence cs) {
char[] chs = str.toCharArray();
int i=0,j=chs.length-1,k=0,l=cs.length();
//String str = "Hello Java";
// 0123456789
//CharSequence cs = "llo";
while(i<j) {
if(str.charAt(i)!=cs.charAt(k)) {
i++;
}
if(str.charAt(i)==cs.charAt(k)) {
}
}
return false;
}
I was just practicing my algorithm skills and got stuck.
Any advice?
Using Only 1 Loop
I did some addition to Poran answer and It works totally fine:
public static boolean contains(String main, String Substring) {
boolean flag=false;
if(main==null && main.trim().equals("")) {
return flag;
}
if(Substring==null) {
return flag;
}
char fullstring[]=main.toCharArray();
char sub[]=Substring.toCharArray();
int counter=0;
if(sub.length==0) {
flag=true;
return flag;
}
for(int i=0;i<fullstring.length;i++) {
if(fullstring[i]==sub[counter]) {
counter++;
} else {
counter=0;
}
if(counter==sub.length) {
flag=true;
return flag;
}
}
return flag;
}
This should work fine..I am printing execution to help understand the process.
public static boolean isSubstring(String original, String str){
int counter = 0, oLength = original.length(), sLength = str.length();
char[] orgArray = original.toCharArray(), sArray = str.toCharArray();
for(int i = 0 ; i < oLength; i++){
System.out.println("counter at start of loop " + counter);
System.out.println(String.format("comparing %s with %s", orgArray[i], sArray[counter]));
if(orgArray[i] == sArray[counter]){
counter++;
System.out.println("incrementing counter " + counter);
}else{
//Special case where the character preceding the i'th character is duplicate
if(counter > 0){
i -= counter;
}
counter = 0;
System.out.println("resetting counter " + counter);
}
if(counter == sLength){
return true;
}
}
return false;
}
Hints:
Use a nested loop.
Extracting the chars to an array is probably a bad idea. But if you are going to do it, you ought to use it!
Ignore the suggestion to use fast string search algorithms. They are only fast for large scale searches. (If you look at the code for String.indexOf, it just does a simple search ...)
As JB Nizet suggested, here is the actual code for contains():
2123 public boolean contains(CharSequence s) {
2124 return indexOf(s.toString()) > -1;
2125 }
And here is the code for indexOf():
1732 public int indexOf(String str) {
1733 return indexOf(str, 0);
1734 }
Which leads to:
1752 public int indexOf(String str, int fromIndex) {
1753 return indexOf(value, offset, count,
1754 str.value, str.offset, str.count, fromIndex);
1755 }
Which finally leads to:
1770 static int indexOf(char[] source, int sourceOffset, int sourceCount,
1771 char[] target, int targetOffset, int targetCount,
1772 int fromIndex) {
1773 if (fromIndex >= sourceCount) {
1774 return (targetCount == 0 ? sourceCount : -1);
1775 }
1776 if (fromIndex < 0) {
1777 fromIndex = 0;
1778 }
1779 if (targetCount == 0) {
1780 return fromIndex;
1781 }
1782
1783 char first = target[targetOffset];
1784 int max = sourceOffset + (sourceCount - targetCount);
1785
1786 for (int i = sourceOffset + fromIndex; i <= max; i++) {
1787 /* Look for first character. */
1788 if (source[i] != first) {
1789 while (++i <= max && source[i] != first);
1790 }
1791
1792 /* Found first character, now look at the rest of v2 */
1793 if (i <= max) {
1794 int j = i + 1;
1795 int end = j + targetCount - 1;
1796 for (int k = targetOffset + 1; j < end && source[j] ==
1797 target[k]; j++, k++);
1798
1799 if (j == end) {
1800 /* Found whole string. */
1801 return i - sourceOffset;
1802 }
1803 }
1804 }
1805 return -1;
1806 }
I came up with this:
public static boolean isSubString(String s1, String s2) {
if (s1.length() > s2.length())
return false;
int count = 0;
//Loop until count matches needle length (indicating match) or until we exhaust haystack
for (int j = 0; j < s2.length() && count < s1.length(); ++j) {
if (s1.charAt(count) == s2.charAt(j)) {
++count;
}
else {
//Redo iteration to handle adjacent duplicate char case
if (count > 0)
--j;
//Reset counter
count = 0;
}
}
return (count == s1.length());
}
I have recently stumbled upon this problem, and though I would share an alternative solution. I generate all the sub strings with length of the string we looking for, then push them into a hash set and check if that contains it.
static boolean contains(String a, String b) {
if(a.equalsIgnoreCase(b)) {
return true;
}
Set<String> allSubStrings = new HashSet<>();
int length = b.length();
for(int i=0; i<a.length(); ++i) {
if(i+length <= a.length()) {
String sub = a.substring(i, i + length);
allSubStrings.add(sub);
}
}
return allSubStrings.contains(b);
}
public static boolean contains(String large, String small) {
char[] largeArr = large.toCharArray();
char[] smallArr = small.toCharArray();
if (smallArr.length > largeArr.length)
return false;
for(int i = 0 ; i <= largeArr.length - smallArr.length ; i++) {
boolean result = true ;
for(int j = 0 ; j < smallArr.length ; j++) {
if(largeArr[i+j] != smallArr[j]) {
result = false;
break;
}
result = result && (largeArr[i+j]==smallArr[j]);
}
if(result==true) {return true;}
}
return false;
}
Certainly not the most efficient solution due to the nested loop, but it seems to work pretty well.
private static boolean contains(String s1, String s2) {
if (s1.equals(s2)) return true;
if (s2.length() > s1.length()) return false;
boolean found = false;
for (int i = 0; i < s1.length() - s2.length(); i++) {
found = true;
for (int k = 0; k < s2.length(); k++)
if (i + k < s1.length() && s1.charAt(i + k) != s2.charAt(k)) {
found = false;
break;
}
if (found) return true;
}
return false;
}
It can be done using a single loop.
public boolean StringContains(String full, String part) {
long st = System.currentTimeMillis();
if(full == null || full.trim().equals("")){
return false;
}
if(part == null ){
return false;
}
char[] fullChars = full.toCharArray();
char[] partChars = part.toCharArray();
int fs = fullChars.length;
int ps = partChars.length;
int psi = 0;
if(ps == 0) return true;
for(int i=0; i< fs-1; i++){
if(fullChars[i] == partChars[psi]){
psi++; //Once you encounter the first match, start increasing the counter
}
if(psi == ps) return true;
}
long et = System.currentTimeMillis()- st;
System.out.println("StringContains time taken =" + et);
return false;
}

Categories

Resources