Palindrome gets terminated - java

Main Class (required)
import java.util.*;
public class FindingPalindrome {
private String inputString;
private Stack<Character> stack = new Stack<Character>();
public FindingPalindrome(String str)
{
inputString = str;
fillStack();
}
public void fillStack()
{
for(int i = 0; i < inputString.length(); i++)
{
stack.push(inputString.charAt(i));
}
}
public String reverseString()
{
String result = new String();
while(!stack.isEmpty())
{
result = result.concat(Character.toString(stack.pop()));
}
return result;
}
public boolean isPalindrome()
{
if(inputString.equalsIgnoreCase(reverseString()))
return true;
else return false;
}
}
Tester Class (required)
import java.util.*;
public class TestPalindrome
{
private static Scanner s;
public static void main(String args[])
{
s = new Scanner(System.in);
System.out.println("Enter the string");
// Read the data
String st1=s.nextLine();
// Create StringBuffer obj for st1
StringBuffer sb=new StringBuffer(st1);
// Reverse the letters
sb.reverse();
st1 = st1.toLowerCase().replaceAll("[^a-z]","");
// Check & Print if palindrome
if(st1.equals(sb.toString()))
System.out.println("Palindrome String");
}
}
Whenever I add "Stop! pots" the code terminates itself and doesn't print the output. I also added the replaceAll(), but it didn't work either. Simple palindrome works "ada", "Kayak", but palindrome with spaces and characters is not working

You are doing it in the wrong order:
// Read the data
String st1=s.nextLine();
// Create StringBuffer obj for st1
StringBuffer sb=new StringBuffer(st1);
// Reverse the letters
sb.reverse();
st1 = st1.toLowerCase().replaceAll("[^a-z]",""); // <<<<<<< too late.
// You created sb with the original
// including punctuation
// Check & Print if palindrome
if(st1.equals(sb.toString()))
System.out.println("Palindrome String");
Replace with
// Read the data
String st1=s.nextLine();
st1 = st1.toLowerCase().replaceAll("[^a-z]",""); // <<<< moved this
// Create StringBuffer obj for st1
StringBuffer sb=new StringBuffer(st1); // <<<< now this is a copy without punctuation
// Reverse the letters
sb.reverse();
// Check & Print if palindrome
if(st1.equals(sb.toString()))
System.out.println("Palindrome String");

Related

Palindrome number check- issue with output

I tried to write a program to check whether a number is a palindrome or not in Java. I tried to convert int to String, and using built-in methods, wrote this logic. But I don't know why I am getting incorrect output for the given input.
class Main {
public static void main(String[] args) {
int x=1213;
StringBuilder s= new StringBuilder();
s.append(x);
StringBuilder s2=new StringBuilder();
s2=s.reverse();
if((s.toString()).equals(s2.toString()))
{
System.out.println(x+" is a palindrome number");
}
else{
System.out.println(x+"is not a palindrome number");
}
}
s2=s.reverse();
Here the StringBuilder class is not immutable , reverse operation will reverse the content of the original the StringBuilder s, you should construct a new StringBuilder here :
public class Main {
public static void main(String[] args) {
int x=1213;
StringBuilder s= new StringBuilder();
s.append(x);
StringBuilder s2=new StringBuilder();
s2=new StringBuilder(s).reverse();
if((s.toString()).equals(s2.toString()))
{
System.out.println(x+" is a palindrome number");
}
else{
System.out.println(x+"is not a palindrome number");
}
}
}
You call s.reverse(), which reverses s in place; and you assign it to s2, so s and s2 are the same object.
You don't need two StringBuilders at all, since you only need to make one modification.
StringBuilder sb = new StringBuilder();
sb.append(x);
sb.reverse();
if (sb.toString().equals(String.valueOf(x))) {
// the number is a palindrome
}

how to compare two strings visually in java?

As of now I am making a small program that compares two string with the outcome of true and false. However, the program needs to say true if it visually looks the same. for example if it say box and b0x then it would be true. As of now the outcome is looking false as shown below.
Enter First String:
box
Enter Second String:
b0x
false
the string below needs to be considered the same
0, o and Q
1, I and T
2 and Z
5 and S
8 and B
below is my current work
import java.util.Scanner;
public class Program {
public static void main(String[] args) {
{
Scanner sc = new Scanner(System.in);
System.out.println("Enter First String:");
String str1 = sc.nextLine();
System.out.println("Enter Second String:");
String str2 = sc.nextLine();
sc.close();
String string1 = new String("0");
String string2 = new String("o");
String string3 = new String("q");
String string4 = new String("1");
String string5 = new String("l");
String string6 = new String("T");
String string7 = new String("2");
String string8 = new String("z");
String string9 = new String("5");
String string10 = new String("s");
String string11 = new String("8");
String string12 = new String("b");
// Comparing for String 3 = String 4
if (str1.equals(str2))
{
System.out.print(true);
}
else if(string1.equals(str1))
{
System.out.print(true);
}
else if(string2.equals(str2))
{
System.out.print(true);
}
else
{
System.out.print(false);
}
}
}
}
Is there any algorithm that I can use or any way where the program can detect as true even when they are visually the same. I appreciate any help, thank you
The answer to this question (as well as most questions about pattern matching in Strings) is regular expressions. All you need to do is use replaceAll for all your character transformations to normalize your strings.
like:
str1 = str1.replaceAll("[oQ]", 0);
str1 = str1.replaceAll("[IT]", 1);
First of all, when you declare String variables, you don't have to make a constructor call each time.
String string1 = "0" // that is fine. No need to call constructor.
Then, I advise you to create a collection of all the characters that are supposed to look the same.
Iterate over all the characters of the first input, and check if :
each character of the first input is equal to each character of the second input
if it is a "look visually the same character", check if second input contains the associated(s) character(s).
According to the data you provided, I suggest you this solution, though it is not the perfect one :
import javafx.util.Pair;
import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;
public class Main {
private static List<List<Character>> charactersVisuallyLookingTheSame = new ArrayList<>();
public static void main(String[] args) {
initCharactersThatLookTheSame();
Scanner sc = new Scanner(System.in);
System.out.println("Enter First String:");
String str1 = sc.nextLine();
System.out.println("Enter Second String:");
String str2 = sc.nextLine();
sc.close();
boolean equal = equalsVisually(str1, str2);
System.out.println(equal);
}
private static boolean equalsVisually(String first, String second)
{
// some checks just in case...
if(first == null || second == null)
{
return false;
}
// to be equal visually, they must have the same length.
if(first.length() != second.length())
{
return false;
}
char[] firstAsArray = first.toCharArray();
char[] secondAsArray = second.toCharArray();
for(int i = 0; i < firstAsArray.length; i++)
{
// if it is different
if(firstAsArray[i] != secondAsArray[i])
{
if(!isCharVisuallyLookingTheSame(firstAsArray[i], secondAsArray[i]))
{
return false;
}
}
}
return true;
}
private static boolean isCharVisuallyLookingTheSame(char first, char second)
{
// we check if it looks visually the same
for(List<Character> visuallyTheSameList : charactersVisuallyLookingTheSame)
{
boolean doesFirstStringContainVisualChar = false;
for(Character c1 : visuallyTheSameList)
{
if(first == c1)
{
boolean doesSecondStringCharVisuallyEquals = false;
for(Character c2 : visuallyTheSameList)
{
if((second == c2))
{
return true;
}
}
}
}
}
return false;
}
private static void initCharactersThatLookTheSame()
{
// these lists contain all the characters that look visually the same.
// add in here any list of characters that visually look the same.
List<Character> o = new ArrayList<>();
charactersVisuallyLookingTheSame.add(o);
o.add('0');
o.add('o');
o.add('Q');
List<Character> i = new ArrayList<>();
charactersVisuallyLookingTheSame.add(i);
i.add('1');
i.add('I');
i.add('T');
List<Character> z = new ArrayList<>();
charactersVisuallyLookingTheSame.add(z);
z.add('2');
z.add('Z');
List<Character> S = new ArrayList<>();
charactersVisuallyLookingTheSame.add(S);
S.add('5');
S.add('S');
List<Character> B = new ArrayList<>();
charactersVisuallyLookingTheSame.add(B);
B.add('8');
B.add('B');
}
}
Some outputs :
I guess that will do the job. don't hesitate to execute it in debug mode if there are any problems. I fast coded this and I could have made mistakes.
But overall, I suggest you to : use regular expressions. It was suggested by another answer and I think that can only be better than this. Nevertheless, regular expressions can be hard to understand...
The other option would be to build a Map with a common Identifier between similar values. Might be a bit more complicated, but should be more performant than looping a replaceAll multiple times to normalize both values.
import java.util.HashMap;
import java.util.Map;
public class VisuallySimilar
{
public static int id = 0;
public static Map<Character, Integer> map = new HashMap<>();
public static void similarChars(Character... chars) {
for(Character c : chars) {
map.put(c, id);
}
id++;
}
public static boolean areSimilar(String val1, String val2) {
if(val1.length() != val2.length())
return false;
char[] char1 = val1.toCharArray();
char[] char2 = val2.toCharArray();
for(int i = 0; i < char1.length; i++) {
if(char1[i] == char2[i] || map.get(char1[i]) == map.get(char2[i]))
continue;
return false;
}
return true;
}
public static void main(String[] args) {
similarChars('0', 'o', 'O', 'Q');
similarChars('T', 'I', '1');
String val1 = "b0x";
String val2 = "box";
System.out.println("Are Similar: " + areSimilar(val1, val2));
}
}

How do I replace more than one type of Character in Java String

newbie here. Any help with this problem would be appreciated:
You are given a String variable called data that contain letters and spaces only. Write the Java class to print a modified version of the String where all lowercase letters are replaced by ? and all whitespaces are replaced by +. An example is shown below: I Like Java becomes I+L???+J???.
What I have so far:
public static void main (String[] args) {
Scanner input = new Scanner(System.in);
String data;
//prompt
System.out.println("Enter a sentence: ");
//input
data = input.nextLine();
for (int i = 0; i < data.length(); i++) {
if (Character.isWhitespace(data.charAt(i))) {
data.replace("", "+");
if (Character.isLowerCase(data.charAt(i))) {
data.replace(i, i++, ); //not sure what to include here
}
} else {
System.out.print(data);
}
}
}
any suggestions would be appreciated.
You can do it in two steps by chaining String#replaceAll. In the first step, replace the regex, [a-z], with ?. The regex, [a-z] means a character from a to z.
public class Main {
public static void main(String[] args) {
String str = "I Like Java";
str = str.replaceAll("[a-z]", "?").replaceAll("\\s+", "+");
System.out.println(str);
}
}
Output:
I+L???+J???
Alternatively, you can use a StringBuilder to build the desired string. Instead of using a StringBuilder variable, you can use String variable but I recommend you use StringBuilder for such cases. The logic of building the desired string is simple:
Loop through all characters of the string and check if the character is a lowercase letter. If yes, append ? to the StringBuilder instance else if the character is whitespace, append + to the StringBuilder instance else append the character to the StringBuilder instance as it is.
Demo:
public class Main {
public static void main(String[] args) {
String str = "I Like Java";
StringBuilder sb = new StringBuilder();
int len = str.length();
for (int i = 0; i < len; i++) {
char ch = str.charAt(i);
if (Character.isLowerCase(ch)) {
sb.append('?');
} else if (Character.isWhitespace(ch)) {
sb.append('+');
} else {
sb.append(ch);
}
}
// Assign the result to str
str = sb.toString();
// Display str
System.out.println(str);
}
}
Output:
I+L???+J???
If the requirement states:
The first character of each word is a letter (uppercase or lowercase) which needs to be left as it is.
Second character onwards can be any word character which needs to be replaced with ?.
All whitespace characters of the string need to be replaced with +.
you can do it as follows:
Like the earlier solution, chain String#replaceAll for two steps. In the first step, replace the regex, (?<=\p{L})\w, with ?. The regex, (?<=\p{L})\w means:
\w specifies a word character.
(?<=\p{L}) specifies a positive lookbeghind for a letter i.e. \p{L}.
In the second step, simply replace one or more whitespace characters i.e. \s+ with +.
Demo:
public class Main {
public static void main(String[] args) {
String str = "I like Java";
str = str.replaceAll("(?<=\\p{L})\\w", "?").replaceAll("\\s+", "+");
System.out.println(str);
}
}
Output:
I+l???+J???
Alternatively, again like the earlier solution you can use a StringBuilder to build the desired string. Loop through all characters of the string and check if the character is a letter. If yes, append it to the StringBuilder instance and then loop through the remaining characters until all characters are exhausted or a space character is encountered. If a whitespace character is encountered, append + to the StringBuilder instance else append ? to it.
Demo:
public class Main {
public static void main(String[] args) {
String str = "I like Java";
StringBuilder sb = new StringBuilder();
int len = str.length();
for (int i = 0; i < len; i++) {
char ch = str.charAt(i++);
if (Character.isLetter(ch)) {
sb.append(ch);
while (i < len && !Character.isWhitespace(ch = str.charAt(i))) {
sb.append('?');
i++;
}
if (Character.isWhitespace(ch)) {
sb.append('+');
}
}
}
// Assign the result to str
str = sb.toString();
// Display str
System.out.println(str);
}
}
Output:
I+l???+J???
package com.company;
import java.util.*;
public class dat {
public static void main(String[] args) {
System.out.println("enter the string:");
Scanner ss = new Scanner(System.in);
String data = ss.nextLine();
for (int i = 0; i < data.length(); i++) {
char ch = data.charAt(i);
if (Character.isWhitespace(ch))
System.out.print("+");
else if (Character.isLowerCase(ch))
System.out.print("?");
else
System.out.print(ch);
}
}
}
enter the string:
i Love YouU
?+L???+Y??U
Firstly, you are trying to make changes to String object which is immutable. Simple way to achieve what you want is convert string to character array and loop over array items:
Scanner input = new Scanner(System.in);
String data;
//prompt
System.out.println("Enter a sentence: ");
//input
data = input.nextLine();
char[] dataArray = data.toCharArray();
for (int i = 0; i < dataArray.length; i++) {
if (Character.isWhitespace(dataArray[i])) {
dataArray[i] = '+';
} else if (Character.isLowerCase(dataArray[i])) {
dataArray[i] = '?';
}
}
System.out.print(dataArray);
See the below code and figure out what's wrong in your code. To include multiple regex put the char within square brackets:
import java.util.Scanner;
public class mainClass {
public static void main(String[] args) {
Scanner input = new Scanner(System.in);
System.out.print("Enter a sentence: ");
String data = input.nextLine();
String one = data.replaceAll(" ", "+");
String two = one.replaceAll("[a-z]", "?");
System.out.println(two);
}
}
You can use String.codePoints method to get a stream over int values of characters of this string, and process them:
private static String replaceCharacters(String str) {
return str.codePoints()
.map(ch -> {
if (Character.isLowerCase(ch))
return '?';
if (Character.isWhitespace(ch))
return '+';
return ch;
})
.mapToObj(Character::toString)
.collect(Collectors.joining());
}
public static void main(String[] args) {
System.out.println(replaceCharacters("Lorem ipsum")); // L????+?????
System.out.println(replaceCharacters("I Like Java")); // I+L???+J???
}
See also: Replace non ASCII character from string

Generate palindrome words

So, I have this code which generates palindrome words in a special manner.
1> it joins the word by its reverse(excluding last character).
2> the words which end with repeated alphabets, for example ABB becomes ABBA and not ABBBA and XAZZZ becomes XAZZZAX.
I am already done with the first part. I have just tried second one by extracting last two characters, because to be honest, I don't know how should I do it.
import java.io.*;
class ISC_Q3_2019
{
public static void main(String args[])throws IOException
{
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
ISC_Q3_2019 ob = new ISC_Q3_2019();
System.out.println("Enter your sentence");
String s = br.readLine();
s=s.toUpperCase();
String words[] = s.split(" ");
int l=words.length;
char ch1=s.charAt(s.length()-1);
String ans=" ", copy=" ", p=" ";
if(ch1=='.'||ch1=='!'||ch1=='?')
{
for(int i=0;i<l;i++)
{
if(ob.isPalindrome(words[i])==true)
{
ans=ans+words[i];
}
else
{
copy=words[i];
words[i]=ob.Reverse(words[i]);
p=copy.concat(words[i]);
ans=ans+p;
}
}
System.out.println("OUTPUT:" +ans.trim());
}
else
System.out.println("Invalid Input!");
}
boolean isPalindrome(String s)
{
s=s.toUpperCase();
int l=s.length();
char ch;
String rev=" ", copy=" ";
copy=s;
for(int i=l-1;i>=0;i--)
{
ch=s.charAt(i);
rev=rev+ch;
}
if(rev.equals(copy))
return true;
else
return false;
}
String Reverse(String s)
{
s=s.toUpperCase();
int l=s.length();
char ch, ch1, ch2;
String r=" ";
for(int i=l-2;i>=0;i--)
{
ch=s.charAt(i);
ch1=s.charAt(l-1);
ch2=s.charAt(l-2);
if(ch1==ch2)
r=r+ch;
else
r=r+ch;
}
return r;
}
}
OUTPUT:
Enter your sentence
The abb is flying.
**OUTPUT:**THE HTABB BAIS IFLYING. GNIYLF
And another part I am concerned is the unmatched spaces.
Here you go
import java.util.Arrays;
import java.util.List;
import java.util.Scanner;
import java.util.stream.Collectors;
public class Palindrome {
public static void main(String... args) {
// Request for input
Scanner reader = new Scanner(System.in);
System.out.println("Enter your sentence...");
// Read the user input
String sentence = reader.nextLine();
// Split the sentence (into tokens) at spaces and special characters using regex
// Keep the special characters where they are and form a List with the split words
List<String> tokens = Arrays.asList(sentence.split("((?<=[\\?,\\. ])|(?=[\\?,\\. ]))"));
// For every token/word, form the palindrome of that and then join them back
String result = tokens.stream().map(s -> formPalindrome(s)).collect(Collectors.joining());
// This is the final result
System.out.println("result: " + result);
reader.close();
}
private static String formPalindrome(String str) {
// Reverse the String
String reversed = new StringBuilder(str).reverse().toString();
// String length
int strLen = reversed.length();
// Compare each character of reversed string with last character of the string until they are different
// When they are different concat the substring with original string
for (int i = 0; i < strLen; i++) {
if (reversed.charAt(i) != str.charAt(strLen - 1)) {
return str + reversed.substring(i);
}
}
return str;
}
}
Here is an idea* that you can build on to get the desired result:
Check the original Strings characters in reverse and count how
many occurences there are
Create a new String from the start of the original String, up
to the end less the count of occurences
Reverse that new String
Concatenate the original String with the new String
So a quickly thrown together example:
int count = 0;
for (int i = s.length() - 1; i > 0; i--) {
if (s.charAt(i) == s.charAt(i - 1)) {
count++;
} else {
break;
}
}
StringBuilder sb = new StringBuilder(s.substring(0, s.length() - 1 - count)).reverse();
System.out.println(s + sb.toString());
Which would give "ABBA" for "ABB" and "XAZZAX" for "XAZZZ".
* It's only an idea and there are probably edge cases etc that aren't catered for but it's merely to give the OP an idea of how to approach it

Capitalize every word using Scanner(System.in) Java

This code should allow the user to input a sentence, change it to lower case, and then capitalize the first letter of each word. But I can't get the scanner to work, it just prints nothing. Any suggestions?
public class Capitalize
{
public static void capCase(String theString)
{
String source = theString;
StringBuffer res = new StringBuffer();
char[] chars = theString.toLowerCase().toCharArray();
boolean found = false;
for(int i = 0; i<chars.length; i++)
{
if(!found&& Character.isLetter(chars[i])){
chars[i] = Character.toUpperCase(chars[i]);
found = true;
} else if (Character.isWhitespace(chars[i])){
found = true;
}
}
}
public static void main(String[] args)
{
Scanner scanner=new Scanner(System.in);
System.out.println(scanner.next());
}
}
Problems as I see them:
The code as it stands will only print the first word typed in once the user presses enter
The method doesn't return anything, so effectively it does all that work and discards it.
So here is what I might do:
I'm going to put everything in main for the sake of concision
public class Capitalize {
public static void main(String[] args) {
Scanner s = new Scanner(System.in);
String sentence = Scanner.nextLine();
StringBuilder ans = new StringBuilder(); // result
for(String s : sentence.split(" ")) { // splits the string at spaces and iterates through the words.
char[] str = s.toLowerCase().toCharArray(); // same as in OPs code
if(str.Length>0) // can happen if there are two spaces in a row I believe
str[0]=Character.toUpperCase(str[0]); // make the first character uppercase
ans.Append(str); // add modified word to the result buffer
ans.Append(' '); // add a space
}
System.out.println(ans);
}
}
You forgot to call the capCase() method, your code only asks for input from stdin and prints it out straight
I tried running the program in main method it runs fine for me. But if you want to get the whole sentence you will have to call scanner like an iterator and then get each next token bu calling scanner.next() method Scanner deliminates words in a sentence on the basis of white spaces. my example implementation is as follows. The you can pass each word in the your function to process it.
`public static void main(String[] args) {
Scanner scanner=new Scanner(System.in);
while (scanner.hasNext())
System.out.println(scanner.next());
}`
I would probably do this
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
while (scanner.hasNextLine()) { // While there is input.
String line = scanner.nextLine(); // read a line.
int i = 0;
for (String s : line.split(" ")) { // split on space... word(s).
if (i != 0) {
System.out.print(" "); // add a space, except for the first word on a line.
}
System.out.print(capCase(s)); // capCase the word.
i++; // increment our word count.
}
System.out.println(); // add a line.
System.out.flush(); // flush!
}
}
public static String capCase(String theString) {
if (theString == null) {
return ""; // Better safe.
}
StringBuilder sb = new StringBuilder(theString
.trim().toLowerCase()); // lowercase the string.
if (sb.length() > 0) {
char c = sb.charAt(0);
sb.setCharAt(0, Character.toUpperCase(c)); // uppercase the first character.
}
return sb.toString(); // return the word.
}
Problem :
1.you need to send the complete Line and send the String to the function capCase()
2.You are not returning the char array back to the caller.
Solution
1.use the below statement to read complete Line
String str=scanner.nextLine();
2.Change return type of capCase() from void to char[] as below:
public static char[] capCase(String theString)
you should return the char[] variable chars from capCase() function as below:
return chars;
Complete Code:
public static char[] capCase(String theString)
{
String source = theString;
StringBuffer res = new StringBuffer();
char[] chars = theString.toLowerCase().toCharArray();
boolean found = false;
for(int i = 0; i<chars.length; i++)
{
if(!found&& Character.isLetter(chars[i])){
chars[i] = Character.toUpperCase(chars[i]);
found = true;
} else if (Character.isWhitespace(chars[i])){
found = true;
}
}
return chars;
}
public static void main(String[] args)
{
Scanner scanner=new Scanner(System.in);
String str=scanner.nextLine();
System.out.println(capCase(str));
}
Try,
public static void main(String[] args) {
System.out.println(capCase("hello world"));
}
public static String capCase(String theString) {
StringBuilder res = new StringBuilder();
String[] words=theString.split(" +");
for (String word : words) {
char ch=Character.toUpperCase(word.charAt(0));
word=ch+word.substring(1);
res.append(word).append(" ");
}
return res.toString();
}
Try this code it worked for me:
import java.util.Scanner;
public class Capitalize {
/**
* This code should allow the user to input a sentence, change it to lower
* case, and then capitalize the first letter of each word. But I can't get
* the scanner to work, it just prints nothing. Any suggestions?
*
* #param theString
*/
public static void capCase(String theString) {
String source = theString.trim();
StringBuffer res = new StringBuffer();
String lower = theString.toLowerCase();
String[] split = lower.split(" ");
for (int i = 0; i < split.length; i++) {
String temp = split[i].trim();
if (temp.matches("^[a-zA-Z]+")) {
split[i] = temp.substring(0, 1).toUpperCase()
+ temp.substring(1);
}
res.append(split[i] + " ");
}
System.out.println(res.toString());
}
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
capCase(scanner.nextLine());
// System.out.println(scanner.next());
}
}
I've tested it. It works.
import java.util.Scanner;
import org.apache.commons.lang3.text.WordUtils;
public class Capitalize {
public static void main(String[] args) {
Scanner s = new Scanner(System.in);
while(s.hasNextLine()) {
System.out.println(WordUtils.capitalize(s.nextLine()));
}
}
}

Categories