I have a Java Assignment where I have to prompt for a line input, check if its a palindrome and then say if the palindrome is made of all text, all numbers, or mixed. I haven't added the part where I check what kind of palindrome it is yet, but I need help with the code to check if it's a palindrome. The code I posted below recognizes everything as a palindrome even if it isn't. This is basic Java so I'm limited to what I used below.
import java.util.Scanner;
public class Project4{
public static void main (String [] args)
{
String line = getInputLine();
while (!isEmptyLine (line))
{
if (isPalindrome (line))
System.out.println ("\"" + line + "\" is a palindrome.");
else
System.out.println ("\"" + line + "\" is not a palindrome");
line = getInputLine();
}
System.out.println ("End of program");
}
public static String getInputLine ( )
{
Scanner in = new Scanner(System.in);
System.out.print("Enter a line of input: ");
String inputline = in.nextLine();
return inputline;
}
public static boolean isEmptyLine(String str)
{
boolean truefalse;
if(str.length()==0)
truefalse = true;
else
truefalse = false;
return truefalse;
}
public static boolean isPalindrome(String str)
{
int left = 0;
int right = str.length();
boolean okay = true;
char ch1; char ch2;
while(okay && left<right)
{
ch1 = str.charAt(left);
if(!Character.isDigit(ch1)||!Character.isLetter(ch1))
left++;
else
{
ch2 = str.charAt(right);
if(!Character.isDigit(ch2)||!Character.isLetter(ch2))
right--;
else
{
ch1 = Character.toUpperCase(ch1);
ch2 = Character.toUpperCase(ch2);
if(ch1==ch2)
{
left++;
right--;
}
else
okay = false;
}
}
}
return okay;
}
}
You need to do logical AND of the 2 checks instead of OR -
if(!Character.isDigit(ch1) && !Character.isLetter(ch1))
Use a method like the following:
boolean isPalindrome (String input) {
int strLength = input.length;
for (int i=0; i < input.length/2; ++i) {
if (input.charAt(i) != input.charAt(strLength-i)) {
return false;
}
}
return true;
}
A late answer although it might help some in the future. The method posted below doesn't use any of StringBuilder functions.
public boolean isPalindrome(String value) {
boolean isPalindrome = true;
for (int i = 0 , j = value.length() - 1 ; i < j ; i ++ , j --) {
if (value.charAt(i) != value.charAt(j)) {
isPalindrome = false;
}
}
return isPalindrome;
}
Related
I'm making a Palindrome Generator. Basically the user inputs a word or sentence and the program outputs whether or not its a Palindrome, which is a word that is spelled the same forwards and backwards like "wow" or "racecar". My program works fine, however the output text will repeat itself like fifty times and I can't seem to figure out where the issue is without messing everything up. Help would be appreciated.
import javax.swing.JOptionPane;
public class palindromedectector {
public static void main(String[] args) {
String testStrings = "";
testStrings = JOptionPane.showInputDialog("Enter word: ");
for (int i = 0; i < testStrings.length(); i++)
{
System.out.print("\"" + testStrings + "\"");
if (isPalindrome(stripString(testStrings)))
System.out.println(" is a palindrome.");
else
System.out.println(" is not a palindrome.");
}
}
public static String stripString(String strip)
{
strip = strip.toUpperCase();
String stripped= "";
for (int i= 0; i< strip.length(); i++)
{
if (Character.isLetter(strip.charAt(i)))
stripped += strip.charAt(i);
}
return stripped;
}
public static boolean isPalindrome (String str)
{
boolean status = false;
if (str.length() <= 1)
status = true;
else if (str.charAt(0) == str.charAt(str.length()-1))
{
status = isPalindrome (str.substring(1, str.length()-1));
}
return status;
}
}
Main issue is that you run isPalindrome check for the same string in the loop, probably you wanted to run multiple checks
public static void main(String[] args) {
final int attempts = 5;
for (int i = 0; i < attempts; i++) {
String word = JOptionPane.showInputDialog("Enter word: ");
System.out.print("\"" + word + "\"");
if (isPalindrome(stripString(word))) {
System.out.println(" is a palindrome.");
} else {
System.out.println(" is not a palindrome.");
}
}
}
Also, the main functionality may be implemented in a shorter way:
// use regexp to get rid of non-letters
private static String stripString(String word) {
if (null == word || word.isEmpty()) {
return word;
}
return word.replaceAll("[^A-Za-z]", "").toUpperCase(); // remove all non-letters
}
// use Java Stream API to check letters using half of word length
private static boolean isPalindrome(String word) {
if (null == word) {
return false;
}
final int len = word.length();
if (len < 2) {
return true;
}
return IntStream.range(0, len/2)
.allMatch(i -> word.charAt(i) == word.charAt(len - 1 - i));
}
Basic problem: You are testing if the word is a palindrome testStrings.length() times, ie once for every letter in the word, rather than just once.
Remove the for loop in your main() method.
import java.util.Scanner;
public class Pailindrome {
public static void main(String[] args) {
Scanner sc1 = new Scanner(System.in);
System.out.println("Please enter a word");
String ori = sc1.nextLine();
isPailindrome(ori);
if (isPailindrome(ori))
System.out.println(ori + "is a Pailindrome");
else
System.out.println(ori + "is NOT a Pailindrome");
}
public static boolean isPailindrome(String ori) {
int i = 0;
int j = ori.length() - 1;
while (i < j) {
if (ori.charAt(i) != ori.charAt(j)) {
return false;
}
i++;
j--;
}
return true;
}
}
The code works perfectly I'm just confused how I will get it to work irrespective of the case
inputted by the user. For example aBba is a palindrome but It says it's not in the code I've done. I
would like any help if possible thanks.
You can convert all of the letters to lowerCase before you start the processing.
You can write your own function or use toLowerCase() String function.
import java.util.Scanner;
public class Pailindrome {
public static void main(String[] args) {
Scanner sc1 = new Scanner(System.in);
System.out.println("Please enter a word");
String ori = sc1.nextLine();
ori = ori.toLowerCase();
isPailindrome(ori);
if (isPailindrome(ori))
}
System.out.println(ori + "is a Pailindrome");
} else {
System.out.println(ori + "is NOT a Pailindrome");
}
}
public static boolean isPailindrome(String ori) {
int i = 0;
int j = ori.length() - 1;
while (i < j) {
if (ori.charAt(i) != ori.charAt(j)) {
return false;
}
i++;
j--;
}
return true;
}
Take the input and call toUpper(); that way when you check to see if it is a palindrome, all of the characters are uppercase.
String ori = scr.nextLint();
if(isPalindrome(ori.toUpperCase()))
//do something
Convert all the cases to lowercase/uppercase before checking the palindrome
isPailindrome(ori.toLowerCase());
Zoom in from both ends and adjust the case as required.
public static boolean isPalindrome(String str) {
int len = str.length();
for (int i = 0; i < len >>1; i++) {
if (Character.toLowerCase(str.charAt(i)) !=
Character.toLowerCase(str.charAt(len - i - 1))) {
return false;
}
}
return true;
}
Note: This question is asked for a school assignment. I fell I'm getting close to the true code, there are only a few points left to be taken care of.
I am asked to write a method that receives two strings(s1 and s2) and
checks whether s2 is in s1 case sensitively. If s2 is in s1 it returns the index of the last occurrence of s2, otherwise it returns -1.
So, here is my code:
import java.util.*;
public class homework4 {
public static void main(String args[]) {
Scanner input = new Scanner(System.in);
System.out.println("\nEnter a choice: ");
int choice = input.nextInt();
if(choice == 1) {
System.out.println("Enter firts string: ");
String s1 = input.next();
System.out.println("Enter second string: ");
String s2 = input.next();
System.out.print(contains(s1,s2));
}
else {
//Call other methods...
}
public static int contains (String s1, String s2) {
for(int i = 0; i<s1.length(); i++) {
for(int j = 0; j<s2.length(); j++) {
char ch = s2.charAt(j);
if(s1.charAt(i) == ch) {
return i;
}
}
}
return -1;
}
But this method returns first index of s2 or it is just a copy of IndexOf method.
Output for s1 = aabbccbbe and s2 = bb is 2.
EDIT : #eli's code
import java.util.*;
public class homework4 {
public static void main(String args[]) {
Scanner input = new Scanner(System.in);
System.out.println("\nEnter a choice: ");
int choice = input.nextInt();
if(choice == 1) {
System.out.println("Enter firts string: ");
String s1 = input.next();
System.out.println("Enter second string: ");
String s2 = input.next();
System.out.print(contains(s1,s2));
}
else {
//Call other methods...
}
public static int contains(String s1, String s2) {
int i = s2.length()-1, j = s1.length()-1;
if(i > j)
return -1;
for(; i > -1; i--) {
for(; j >= 0; j--) {
if(s1.charAt(j) == s2.charAt(i)) {
if(i == 0)
return j;
if(j != 0)
j--;
break;
} else if(i != s2.length()) {
i = s2.length()-1;
}
}
}
return -1;
}
First of all, close any resource you open when you're done with it.
input.close();
If it is allowed you can just use regex:
public static int contains (String s1, String s2) {
Pattern p = Pattern.compile(s2+"(?!.*"+s2+")");
Matcher m = p.matcher(s1);
if(m.find())
return m.start();
return -1;
}
The regex pattern is explained here.
With find() you make sure that at least one occurrence is present.
As the pattern can result in 1 and only 1 result, you can just ask for the "first index of first occurrence" in the matcher, achieved with start().
EDIT
Okay, I can see you can't use anything but charAt and length.
Here's a different solution without regex, substring, indexOf or what-so-ever:
public static int contains(String s1, String s2) {
int i = s2.length()-1, j = s1.length()-1;
if(i > j)
return -1;
for(; i > -1; i--) {
for(; j >= 0; j--) {
if(s1.charAt(j) == s2.charAt(i)) {
if(i == 0)
return j;
if(j != 0)
j--;
break;
} else if(i != s2.length()) {
i = s2.length()-1;
}
}
}
return -1;
}
I must admit I didn't thoroughly test this.
FINAL
I've done some minor fixes for you. I don't know how you were capable of compiling what you edited in your post. Here's a working sample:
import java.util.Scanner;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class homework4 {
public static void main(String args[]) {
Scanner input = new Scanner(System.in);
System.out.println("Enter choice: ");
switch (input.nextInt()) {
// If 1 is given as input...
case 1:
// As we press "enter" after inputting 1, the newline is read by the
// scanner. We skip this newline by doing this.
input.nextLine();
System.out.println("Enter first string: ");
String s1 = input.nextLine();
System.out.println("Enter second string: ");
String s2 = input.nextLine();
System.out.println("Result: " + contains(s1, s2));
break;
// If 2 is given as input (just for the sake of the example)
case 2:
System.out.println("You chose an unimplemented choice.");
break;
// If something else is given as input...
default:
System.out.println("Nothing to do...");
break;
}
// As Scanner is considered a resource, we have to close it, now that
// we're done using it.
input.close();
}
// This is the RegEx implementation
public static int containsRegx(String s1, String s2) {
Pattern p = Pattern.compile(s2 + "(?!.*" + s2 + ")");
Matcher m = p.matcher(s1);
if (m.find())
return m.start();
return -1;
}
// This is the charAt and length only
public static int contains(String s1, String s2) {
int i = s2.length() - 1, j = s1.length() - 1;
if(i > j || i * j == 0)
return -1;
for (; i > -1; i--) {
for (; j >= 0; j--) {
if (s1.charAt(j) == s2.charAt(i)) {
if (i == 0)
return j;
if (j != 0)
j--;
break;
} else if (i != s2.length()) {
i = s2.length() - 1;
}
}
}
return -1;
}
}
I think it will boil down to looping through string characters and storing the last index of occurred match.
Here is not perfect, but simple example without use of indexOf:
public static int contains(String s1, String s2) {
if(s1.length() < s2.length())
return -1;
int lastOccurrence = -1;
for (int i = 0; i < s1.length(); ) {
if (s1.startsWith(s2, i)) {
lastOccurrence = i + s2.length() - 1;
i = lastOccurrence + 1;
}
else {
++i;
}
}
return lastOccurrence;
}
Say you have the string called sentence: The quick brown fox jumps over the lazy dog. and you want to find the last occurrence of "the", called token.
sentence.length = 44 and token.length = 3
Consider this somewhat java pseudo code:
public static int lastIndexOf(String sentence, String token) {
//The starting index is the first possible location your token could fit
int startingIndex = sentence.length() - token.length();
//move backwards one character at a time until you reach 0
//checking for string fragment that equals your token at each iteration
for (int i = startingIndex; i >= 0; i--) {
String fragment = sentence.substring(i, i + token.length());
if (fragment.equals(token)) return i;
}
return -1;
}
EDIT
Here is the full application using only length and charAt():
public class HelloWorld
{
// arguments are passed using the text field below this editor
public static void main(String[] args)
{
int indexOf = lastIndexOf("The quick brown fox jumps over the lazy dog.", "the");
System.out.print(indexOf);
}
public static int lastIndexOf(String sentence, String token) {
int startingIndex = sentence.length() - token.length();
for (int i = startingIndex; i >= 0; i--) {
String fragment = substring(sentence, i, i + token.length());
if (strEquals(token, fragment)) return i;
}
return -1;
}
public static String substring(String str, int startingIndex, int endingIndex) {
int size = endingIndex - startingIndex;
char[] arr = new char[size];
for (int i = 0; i < size; i++) {
arr[i] = str.charAt(startingIndex+i);
}
return new String(arr);
}
public static boolean strEquals(String s1, String s2) {
if (s1.length() != s2.length()) return false;
for (int i = 0; i < s1.length(); i++) {
if (s1.charAt(i) == s2.charAt(i)) continue;
return false;
}
return true;
}
}
EDIT 2
You also have a bug in the way you are reading your input. You need to use input.readLine() to get the full line. input.read breaks on spaces. Along those lines, you also need a new scanner for each line you want to read.
EDIT 3
Here is the whole source:
import java.util.Scanner;
public class HelloWorld {
public static void main(String[] args)
{
Scanner input1 = new Scanner(System.in);
System.out.println("\nEnter a choice: ");
String s1="";
String s2="";
int choice = input1.nextInt();
if(choice == 1) {
Scanner input2 = new Scanner(System.in);
System.out.println("Enter first string: ");
s1 = input2.nextLine();
Scanner input3 = new Scanner(System.in);
System.out.println("Enter second string: ");
s2 = input3.nextLine();
}
int indexOf = lastIndexOf(s1, s2);
System.out.println(indexOf);
}
public static int lastIndexOf(String sentence, String token) {
int startingIndex = sentence.length() - token.length();
for (int i = startingIndex; i >= 0; i--) {
String fragment = substring(sentence, i, i + token.length());
if (strEquals(token, fragment)) return i;
}
return -1;
}
public static String substring(String str, int startingIndex, int endingIndex) {
int size = endingIndex - startingIndex;
char[] arr = new char[size];
for (int i = 0; i < size; i++) {
arr[i] = str.charAt(startingIndex+i);
}
return new String(arr);
}
public static boolean strEquals(String s1, String s2) {
if (s1.length() != s2.length()) return false;
for (int i = 0; i < s1.length(); i++) {
if (s1.charAt(i) == s2.charAt(i)) continue;
return false;
}
return true;
}
}
This question already has answers here:
How do I compare strings in Java?
(23 answers)
Closed 7 years ago.
So this program is supposed to be a game where a user enters a phrase and another user tries to guess the phrase. I'm having a problem with buying a vowel, however. No matter what I enter at line 41 (, it just goes past the loop. I made the validAnswer(String answer) method in the hopes that it would be useful in the loop but it doesn't look to be much help. I know there is a small thing I'm missing but I'm too new to Java to recognize it yet. What am I doing wrong?
I apologize for the long amount of code.
import java.util.Scanner;
public class PhraseGame {
public static void main(String[] args) {
// Initialize scanner
Scanner stdIn = new Scanner(System.in);
// Initialize variables
String sPhrase;
String answer = "f";
char cGuess = 0;
char vGuess = 0;
int count = 0;
int vowels = 0;
int consonants = 0;
int spaces = 0;
boolean gameOver = false;
boolean correct = true;
// Start the "fun" game
System.out.print("Please enter the phrase to guess at: ");
sPhrase = stdIn.nextLine();
// Create the temporary Array
char [] tmpArr = new char[sPhrase.length()];
for (int i = 0; i < sPhrase.length(); i++) {
tmpArr[i] = sPhrase.charAt(i);
}
// Gets the number of spaces
spaces = initTemplateArray(sPhrase, tmpArr, spaces);
printTemplateArray(tmpArr);
while (!(endGame(gameOver, spaces, consonants, vowels, sPhrase))) {
cGuess = getConsonant(stdIn, cGuess);
do {
System.out.print("\nWould you like to buy a vowel?: ");
answer = stdIn.next();
if (answer == "y") {
getVowel(stdIn, vGuess); }
else if (answer == "n"){
break;
}
} while (!validAnswer(answer));
// Updates the array and prints it
updateTemplateArray(tmpArr, sPhrase, cGuess, vGuess, count, vowels, consonants);
printTemplateArray(tmpArr);
// Checks if the game is over
endGame(gameOver, spaces, consonants, vowels, sPhrase);
}
}
// returns the number of space characters used in the common phrase
public static int initTemplateArray(String sPhrase, char [] tmpArr, int spaces) {
for (int i = 0; i < sPhrase.length(); i++) {
if (tmpArr[i] != ' ') {
tmpArr[i] = '?';
} else {
tmpArr[i] = ' ';
spaces++;
}
}
return spaces;
}
public static void printTemplateArray(char [] tmpArr) {
System.out.println("\nCommon Phrase");
System.out.println("-------------");
for (int i = 0; i < tmpArr.length; i++) {
System.out.print(tmpArr[i]);
}
}
public static boolean isVowel(char c) {
return (c == 'a' || c == 'e' || c == 'i' || c == 'o' || c == 'u');
}
public static char getConsonant(Scanner stdIn, char cGuess) {
do {
System.out.println("\nEnter a lowercase consonant guess: ");
cGuess = stdIn.next().charAt(0);
} while (isVowel(cGuess));
return cGuess;
}
public static char getVowel(Scanner stdIn, char vGuess) {
do {
System.out.println("\nEnter a lowercase vowel guess: ");
vGuess = stdIn.next().charAt(0);
} while (!(isVowel(vGuess)));
return vGuess;
}
public static int updateTemplateArray(char [] tmpArr, String sPhrase, char cGuess, char vGuess, int count, int vowels, int consonants) {
for (int i = 0; i < sPhrase.length(); i++) {
if (cGuess == sPhrase.charAt(i)) {
tmpArr[i] = sPhrase.charAt(i);
count++;
consonants++;
}
if (vGuess == sPhrase.charAt(i)) {
tmpArr[i] = sPhrase.charAt(i);
count++;
vowels++;
}
}
return count & vowels & consonants;
}
public static boolean endGame(boolean gameOver, int spaces, int consonants, int vowels, String sPhrase) {
int total = spaces + consonants + vowels;
if (total == sPhrase.length()) {
return true;
}
else {
return false;
}
}
public static boolean validAnswer(String answer) {
if (answer.equalsIgnoreCase("y")) {
return true;
}
else if (answer.equalsIgnoreCase("n")) {
return true;
}
else {
return false;
}
}
}
You need to check for null.
public static boolean validAnswer(String answer) {
if (answer!=null && (answer.equalsIgnoreCase("y") || answer.equalsIgnoreCase("n"))) {
return true;
}
return false;
}
or an other unconventional way.
public static boolean validAnswer(String answer) {
if ("y".equalsIgnoreCase(answer) || "n".equalsIgnoreCase(answer))) {
return true;
}
return false;
}
You need to fix
do {
System.out.print("\nWould you like to buy a vowel?: ");
answer = stdIn.nextLine();
if ("y".equalsIgnoreCase(answer)) {
getVowel(stdIn, vGuess);
} else if ("n".equalsIgnoreCase(answer)){
break;
}
} while (!validAnswer(answer));
Hi i am trying to write a palindrome method but am getting the wrong results
public static boolean isPalindrome(String input){
int b=input.length();
int []array=new int[b];
for(int i=0;i<array.length;i++){
array[i]=Integer.parseInt(input);}
for(int i=0;i<(array.length)/2;i++){
if(!(array[i]==array[array.length-1-i])){
return false;}
}
return true;
}
}
If you put the String into a StringBuilder you can use the .reverse() method. then just check if the 2 are equal.
StringBuilder input = new StringBuilder("helloolleh");
StringBuilder value = input.reverse();
if(value.toString().equals(input.toString()){
//process
}
You can go for the simpler method to check for palindrome.
Use the StringBuilder class and use the .reverse() method to reverse the string and then check for palindrome test.
StringBuilder value1= new StringBuilder("nitin");
StringBuilder value2 = input.reverse();
if(value1.toString().equals(value2.toString()){
System.out.println("This is a palindrome string ..");
}
Or you can go by this way also ..
public static boolean isPalindrome(String word) {
int left = 0;
int right = word.length() -1;
while (left < right) {
if (word.charAt(left) != word.charAt(right)) {
return false;
}
left++;
right--;
}
return true;
}
Not sure why you are using Integer.Parse().
Try something like this (mostly following the logic from the question)
public static boolean isPalindrome(String input) {
char[] array = input.toCharArray();
for (int i = 0; i < (array.length) / 2; i++) {
if (!(array[i] == array[array.length - 1 - i])) {
return false;
}
}
return true;
}
You can use two "pointers" one starting from the beginning of the string and one from the end, and move them in opposite directions checking that characters are equals; as soon as you find a difference you know your string is not palindromic; conversely, if you don't find differences you know the string is palindromic:
public static boolean isPalindome(String input) {
char[] cs = input.toCharArray();
for (int i = 0, j = cs.length - 1; i < j; i++, j--) {
if (cs[i] != cs[j])
return false;
}
return true;
}
import java.util.Scanner;
public class Test_String {
private static boolean IsPalindrome(String s)
{
StringBuffer str1 = new StringBuffer(s);
StringBuffer str2 = str1.reverse();
if(s.equalsIgnoreCase(str2.toString()))
return true;
else
return false;
}
public static void main(String[] args) {
Scanner scan = new Scanner(System.in);
System.out.println("Enter a String to be checked as Palindrome ");
String in = scan.nextLine();
if(IsPalindrome(in))
System.out.println("\nEntered String is a Palindrome ");
else
System.out.println("\nEntered String is NOT a Palindrome ");
}
}