isVowel() method with a character in a String - java

I have a text file with a bunch of words. One part of my program is supposed to, based on the user input, scan this list and insert into the output file the words that contain the requested number of vowels. I have a isVowel method that returns a boolean, but it doesn't seem to work--the output is just an empty list.
Here's the method:
public boolean isVowel(char c)
{
if(c=='a' || c=='A' || c=='e' || c=='E' || c=='i' || c=='I' || c=='o' || c=='O' || c=='u' || c=='U')
{
return true;
}
else
{
return false;
}
}
}
Here's the part of the program where it is used:
public ArrayList<String> vowelHeavy(int n, int m)
{
int vowels = 0;
while(input.hasNextLine())
{
word = input.nextLine();
if (word.length() == n)
{
for(int i = 0; i < word.length(); i++)
{
if(isVowel(word.charAt(i)) == true)
{
vowels++;
}
}
if (vowels == m)
{
output.add(word);
}
}
word = input.nextLine();
}
return output;
}

Your biggest problem is you are not resetting you vowels counting variable when you test a new word. The value just keeps accumulating the total vowels in the file.
Change:
int vowels = 0;
while(input.hasNextLine()) {
...
to:
while(input.hasNextLine()) {
int vowels = 0;
...
As an aside, most of your code, including the isVowel() method, could be eliminated with a single line:
int vowels = word.replaceAll("[^aeiouAEIOU]", "").length();
This works by eliminating from the word all characters that aren't vowels; what's left are the vowels, so just take the length to get the count.

Theres a much easier way to write this code:
public boolean isVowel(char c){
return(your boolean tests);
}

2 things:
If the word.length() == n test is never true, then output is never changed. Please make sure that test is correct.
This statement exists at the top AND bottom of the while loop, causing you to ignore every other input line:
word = input.nextLine();

Related

Java Loops - Password requirements [duplicate]

This question already has answers here:
Get string character by index
(13 answers)
Closed 8 months ago.
Websites commonly require a password that satisfies several requirements. Write a program that checks if an input string satisfies the following (error message is shown for each):
At least 8 characters (Too short)
At least one letter (Missing letter)
At least one number (Missing number)
At least one of these special characters: !, #, % (Missing special)
Output OK, or all related error messages (in above order). If the input string is "Hello", the output is:
Too short
Missing number
Missing special
Hints:
Declare a boolean variable for each requirement.
Use a for loop to visit each character, setting the corresponding boolean to true if satisfied (length is done differently though).
Use the functions Character.isLetter() and Character.isDigit() to detect if a character is a letter or a number.
This is what I have so far for my Java program, but I keep getting errors. Thanks for the help.
import java.util.Scanner;
public class Main {
public static void main(String[] args) {
Scanner scnr = new Scanner(System.in);
String newString;
boolean atLeastEightCharacter;
boolean atLeastOneLetter;
boolean atLeastOneNumber;
boolean atLeastOneSpecialCharacter;
newString = scnr.nextLine();
atLeastEightCharacter = false;
atLeastOneLetter = false;
atLeastOneNumber = false;
atLeastOneSpecialCharacter = false;
if (newString.length() >= 8) {
atLeastEightCharacter = true;
for (int i = 0; i <newString.length(); i++) {
if (Character.isLetter(i)) {
atLeastOneLetter = true;
}
if (Character.isDigit(i)) {
atLeastOneDigit = true;
}
if (newString(i) == '!' || newString(i) == '#' || newString(i)
== '%') {
atLeastOneSpecialCharacter = true;
}
}
}
if (atLeastEightCharacter == false) {
System.out.println("Too short");
}
if (atLeastOneLetter == false) {
System.out.println("Missing letter");
}
if (atLeastOneDigit == false) {
System.out.println("Missing number");
}
if (atLeastOneSpecialCharacter) {
System.out.println("Missing special");
}
}
}
the problem is that you're not checking string's symbols, but indexes, variable i is not char, but integer index
here is fixed version:
for (int i = 0; i <newString.length(); i++) {
char c = newString.charAt(i);
if (Character.isLetter(c)) atLeastOneLetter = true;
if (Character.isDigit(c)) atLeastOneDigit = true;
if (c == '!' || c == '#' || c == '%') atLeastOneSpecialCharacter = true;
}

Registering an invalid piece of data from a pattern

I need to use a six letter word and if it has a sequence of letter number letter number letter number, then it will be a valid piece of data. Otherwise, it will be considered invalid. The problem with my code is, it always runs it as valid. Here is my code:
vstatus=false;
char a=pcode.charAt(0);
char b=pcode.charAt(1);
char c=pcode.charAt(2);
char d=pcode.charAt(3);
char e=pcode.charAt(4);
char f=pcode.charAt(5);
if(!Character.isLetter(a)) vstatus=true;
if(!Character.isDigit(b)) vstatus=true;
if(!Character.isLetter(c)) vstatus=true;
if(!Character.isDigit(d)) vstatus=true;
if(!Character.isLetter(e)) vstatus=true;
if(!Character.isDigit(f)) vstatus=true;
if (vstatus=true)
{
System.out.println(convertUpperCase(pcode)+" is a valid postal code");
}
if (vstatus=false)
{
System.out.println(convertUpperCase(pcode)+" is not a valid postal code");
}
I gues this would be shorter code for your problem:
String pcode = "aza2a3";
String regex = "[A-Za-z]{1}[\\d]{1}[A-Za-z]{1}[\\d]{1}[A-Za-z]{1}[\\d]{1}";
boolean matches = pcode.matches(regex);
System.out.println(matches);
matches is true if your string is in form that you need and false if i does not match your required string
In your code, even if one character is correct and all the others are wrong, you make it true. You need to confirm that all the characters are correct. Use &&.
String pcode = "i8i8i8";
char a=pcode.charAt(0);
char b=pcode.charAt(1);
char c=pcode.charAt(2);
char d=pcode.charAt(3);
char e=pcode.charAt(4);
char f=pcode.charAt(5);
if (Character.isLetter(a) && Character.isDigit(b) && Character.isLetter(c) && Character.isDigit(d) && Character.isLetter(e) && Character.isDigit(f)) {
System.out.println("valid");
} else {
System.out.println("not a valid postal code");
}
Or, in a loop:
String pcode = "i8i8i8";
boolean flag = true;
for (int i = 0; i < pcode.length(); i++) {
if (!(i % 2 == 0 && Character.isLetter(pcode.charAt(i)) || Character
.isDigit(pcode.charAt(i)))) {
flag = false;
}
}
if (flag) { System.out.println("valid"); }
else { System.out.println("not valid"); }
Ideally, extract the code into a method:
static boolean isPcodeValid(String s) {
for (int i = 0; i < s.length(); i++) {
if (!(i % 2 == 0 && Character.isLetter(s.charAt(i)) || Character
.isDigit(s.charAt(i)))) {
return false;
}
}
return true;
}
Or, use some Java8+ features:
static boolean isPcodeValid(String s) {
return IntStream.range(0, s.length())
.allMatch(i -> i % 2 == 0 && Character.isLetter(s.charAt(i)) || Character
.isDigit(s.charAt(i)));
}
Finally,
You may use this regex:
String r = [A-Za-z][\d][A-Za-z][\d][A-Za-z][\d]
if (pcode.matches(r)) {
// valid
} else {
// invalid
}
5 different ways, choose the one that suits you the best.

How do I handle punctuation in this Pig Latin translator?

The rest of the code is working perfectly but I cannot figure out how to prevent punctuation from being translated.
public class PigLatintranslator
{
public static String translateWord (String word)
{
String lowerCaseWord = word.toLowerCase ();
int pos = -1;
char ch;
for (int i = 0 ; i < lowerCaseWord.length () ; i++)
{
ch = lowerCaseWord.charAt (i);
if (isVowel (ch))
{
pos = i;
break;
}
}
if (pos == 0 && lowerCaseWord.length () != 1) //translates if word starts with vowel
{
return lowerCaseWord + "way"; // Adding "way" to the end of string
}
else if (lowerCaseWord.length () == 1) //Ignores words that are only 1 character
{
return lowerCaseWord;
}
else if (lowerCaseWord.charAt(0) == 'q' && lowerCaseWord.charAt(1) == 'u')//words that start with qu
{
String a = lowerCaseWord.substring (2);
return a + "qu" + "ay";
}
else
{
String a = lowerCaseWord.substring (1);
String b = lowerCaseWord.substring (0,1);
return a + b + "ay"; // Adding "ay" at the end of the extracted words after joining them.
}
}
public static boolean isVowel (char ch) checks for vowel
{
if (ch == 'a' || ch == 'e' || ch == 'i' || ch == 'o' || ch == 'u' || ch == 'y')
{
return true;
}
return false;
}
}
I need the translation to ignore punctuation. For example "Question?" should be translated to "estionquay?" (question mark still in the same position and not translated)
As Andreas said, if the function is expecting only one word, it should be the responsibility of the calling function to ensure there's no full sentence or punctuation being passed to it. With that said, if you require the translator to handle this, you need to find the index of the string where the punctuation or non-letter character occurs. I added in a main method to test the function:
public static void main(String[] args) {
System.out.println(translateWord("QUESTION?"));
}
I added a loop into the qu case to find the punctuation being input, the two checks are to see if the character at position i is inside the range of a - z. The sub-string then only goes to the point where the punctuation is found.
int i;
for (i = 0; i < lowerCaseWord.length(); i++) {
if(lowerCaseWord.charAt(i) > 'z' || lowerCaseWord.charAt(i) < 'a') {
break;
}
}
String a = lowerCaseWord.substring (2, i);
String b = lowerCaseWord.substring(i);
return a + "qu" + "ay" + b;
This may need some tweaking if you're worried about words with hyphens and whatnot but this should put across the basic idea.
Here's the output I received:
$javac PigLatintranslator.java
$java -Xmx128M -Xms16M PigLatintranslator
estionquay?

Beautiful Word:Hackerrank

Question
We consider a word,w , to be beautiful if the following two conditions are satisfied:
No two consecutive characters are the same.
No two consecutive characters are in the following vowel set: a, e, i, o, u, y. Note that we consider y to be a vowel in this challenge.
For example:
The string batman is beautiful because it satisfies the given criteria; however, apple has two consecutive occurrences of the same letter (pp) and beauty has three consecutive vowels (eau), so those words are not beautiful.
My problem is when i am giving an input string "yes" it prints Yes but it should print No.
When i debugged the code using Intellij i see that
It is executing the code which is past return statement but the return statement is used to transfer control to the main function.
Solution
public class Coding {
int count = 0;
public static void main(String[] args) {
Coding obj = new Coding();
Scanner in = new Scanner(System.in);
String w = in .next();
boolean b = true;
char[] c = w.toCharArray();
for (int i = 0; i < c.length - 2; i++) {
b = obj.check(i, c); //recursive function
if (c[i] == c[i + 1]) {
b = false;
break;
}
if (!b) {
System.out.println("No");
break;
}
}
if (c[c.length - 2] == c[c.length - 1]) //check.for.the.remaining.chars
System.out.println("No");
else if (b) {
System.out.println("Yes");
}
}
public boolean check(int i, char[] c) {
if (c[i] == 'a' || c[i] == 'e' || c[i] == 'i' || c[i] == 'o' || c[i] == 'u' || c[i] == 'y') {
count++;
if (count == 2) {
return false; // code following this statement are executing
}
check(i + 1, c);
}
count = 0;
return true;
}
}
You are making a recursive call, but you are ignoring the results of that call!
That doesn't make sense. Either that call is valid, then you should return whatever comes back. Or the recursion doesn't "belong" there, then you should rework the complete method!
Beyond that: although recursive solution often look elegant, those contests focus on optimal performance. Meaning: rather use a single loop to iterate that string once.
Hint: The problem appears to be with method count. It always returns true to main method. If any recursive call returns false, is it being propagated back to main method?

Why isn't it working for "not xy balanced"?

We'll say that a String is xy-balanced if for all the 'x' chars in the string, there exists a 'y' char somewhere later in the string. So "xxy" is balanced, but "xyx" is not. One 'y' can balance multiple 'x's. Given a string str, Print “xy balanced”if the given string is xy-balanced otherwise print “not xy balanced”.
public static void main(String[] args)
{
Scanner scan = new Scanner(System.in);
String str = scan.next();
int x = str.length();
boolean xyBalanced = false;
for(int i = x - 1; i >= 0; i--)
{
char y = str.charAt(i);
if(y == 'y')
xyBalanced = true;
else if(y == 'x')
xyBalanced = false;
else
xyBalanced = true;
}
if(xyBalanced = true)
System.out.print("xy balanced");
else if(xyBalanced = false)
System.out.print("not xy balanced");
}
It's giving me "xy balanced" when I input aabbx when in fact it should give "not xy balanced". What is wrong with this code?
Why do you check from the end of the string to the start? It is very difficult to understand.
Apart from the if/else issue you have at the end of your program, which you can change to below, your program still doesn't work after I corrected it.
System.out.print(xyBalanced ? "xy balanced" : "not xy balanced");
To check if there is always a 'y' on the right of an 'x', you can use the following loop - basically, an 'x' always set the xyBalanced flag to false and a 'y' always set it to be true.
public static void main(String[] args) {
Scanner scan = new Scanner(System.in);
String str = scan.next();
int length = str.length();
boolean xyBalanced = true;
for (int i = 0; i < length; ++i) {
if (str.charAt(i) == 'x') {
xyBalanced = false;
} else if (str.charAt(i) == 'y') {
xyBalanced = true;
}
}
System.out.print(xyBalanced ? "xy balanced" : "not xy balanced");
}
The statement:
if(xyBalanced = true)
Is an assignment operator, it should be using the == operator:
if(xyBalanced == true){
System.out.print("xy balanced");
} else {
System.out.print("not xy balanced");
}
Since it's a boolean you can also say:
System.out.print( (!xyBalanced? "not" : "") + "xy balanced");
However, from your logic, it seems like you can also say
boolean xyBalanced = str.lastIndexOf('x') < (str.length()-1);
Because you are considering non-x/non-y characters.
So really you can simplify all the code into two lines.
Also there is an issue with your loop. You're actually going from the right to left. Is that intentional?
for(int i = x - 1; i >= 0; i--)
would seem like it should be:
for (int i=0;i<x;i++)
you can do following for identifying balanced string
boolean xyBalanced = inputString.lastIndexOf('x') < inputString.indexOf('y');
indexOf function always returns first occurrence of string. We can check if last index of x is less than first index of y, and variable 'xyBalanced' will be accordingly get true or false.
public boolean xyBalance(String str) {
if(str.endsWith("x")){
System.out.println("false");
return false;
}
if(str.endsWith("y")){
System.out.println("true");
return true;
}
if(str.lastIndexOf("x")>str.lastIndexOf("y")) {
System.out.println("false");
return false;
}
System.out.println("true");
return true;
}

Categories

Resources