can you please explain me this code? i am not able to understand the use of buffer array. how does value at every index become zero?
public static boolean isAnagram(String input1, String input2) {
if(input1 == null || input2 == null || (input1.length() != input2.length())){
return false;
} else {
int[] buffer = new int[26];
for(int i=0; i < input1.length(); i++){
buffer[input1.charAt(i) - 'a']++;
buffer[input2.charAt(i) - 'a']--;
}
for(int j=0; j < buffer.length; j++){
if(buffer[j] != 0) return false;
}
return true;
}
}
buffer holds a use counter for each lower-case character value used in the strings, all zero initially.
Each counter is then incremented for each use of a character in input1, decremented for each use of a character in input2, so if all characters are used the same number of times, all counters will become zero in the end.
This function will likely crash if called with strings that have anything but lower case letters in them.
Related
I have reversed the string and have a for loop to iterate through the reversed string.
I am counting characters and I know I have a logic flaw, but I cannot pinpoint why I am having this issue.
The solution needs to return the length of the last word in the string.
My first thought was to iterate through the string backward (I don't know why I decided to create a new string, I should have just iterated through it by decrementing my for loop from the end of the string).
But the logic should be the same from that point for my second for loop.
My logic is basically to try to count characters that aren't whitespace in the last word, and then when the count variable has a value, as well as the next whitespace after the count has counted the characters of the last word.
class Solution {
public int lengthOfLastWord(String s) {
int count = 0;
int countWhite = 0;
char ch;
String reversed = "";
for(int i = 0; i < s.length(); i++) {
ch = s.charAt(i);
reversed += ch;
}
for(int i = 0; i < reversed.length(); i++) {
if(!Character.isWhitespace(reversed.charAt(i))) {
count++;
if(count > 1 && Character.isWhitespace(reversed.charAt(i)) == true) {
break;
}
}
}
return count;
}
}
Maybe try this,
public int lengthOfLastWord(String s) {
String [] arr = s.trim().split(" ");
return arr[arr.length-1].length();
}
Another option would be to use index of last space and calculate length from it:
public int lengthOfLastWord(String string) {
int whiteSpaceIndex = string.lastIndexOf(" ");
if (whiteSpaceIndex == -1) {
return string.length();
}
int lastIndex = string.length() - 1;
return lastIndex - whiteSpaceIndex;
}
String.lastIndexOf() finds the start index of the last occurence of the specified string. -1 means the string was not found, in which case we have a single word and length of the entire string is what we need. Otherwise means we have index of the last space and we can calculate last word length using lastIndexInWord - lastSpaceIndex.
There are lots of ways to achieve that. The most efficient approach is to determine the index of the last white space followed by a letter.
It could be done by iterating over indexes of the given string (reminder: String maintains an array of bytes internally) or simply by invoking method lastIndexOf().
Keeping in mind that the length of a string that could be encountered at runtime is limited to Integer.MAX_VALUE, it'll not be a performance-wise solution to allocate in memory an array, produced as a result of splitting of this lengthy string, when only the length of a single element is required.
The code below demonstrates how to address this problem with Stream IPA and a usual for loop.
The logic of the stream:
Create an IntStream that iterates over the indexes of the given string, starting from the last.
Discard all non-alphabetic symbols at the end of the string with dropWhile().
Then retain all letters until the first non-alphabetic symbol encountered by using takeWhile().
Get the count of element in the stream.
Stream-based solution:
public static int getLastWordLength(String source) {
return (int) IntStream.iterate(source.length() - 1, i -> i >= 0, i -> --i)
.map(source::charAt)
.dropWhile(ch -> !Character.isLetter(ch))
.takeWhile(Character::isLetter)
.count();
}
If your choice is a loop there's no need to reverse the string. You can start iteration from the last index, determine the values of the end and start and return the difference.
Just in case, if you need to reverse a string that is the most simple and efficient way:
new StringBuilder(source).reverse().toString();
Iterative solution:
public static int getLastWordLength(String source) {
int end = -1; // initialized with illegal index
int start = 0;
for (int i = source.length() - 1; i >= 0; i--) {
if (Character.isLetter(source.charAt(i)) && end == -1) {
end = i;
}
if (Character.isWhitespace(source.charAt(i)) && end != -1) {
start = i;
break;
}
}
return end == -1 ? 0 : end - start;
}
main()
public static void main(String[] args) {
System.out.println(getLastWord("Humpty Dumpty sat on a wall % _ (&)"));
}
output
4 - last word is "wall"
Firstly, as you have mentioned, your reverse string formed is just a copy of your original string. To rectify that,
for (int i = s.length() - 1; i >= 0; i--) {
ch = s.charAt(i);
reversed += ch;
}
Secondly, the second if condition is inside your first if condition. That is why, it will never break ( because you are first checking if character is whitespace, if it is, then you are not going inside the if statement, thus your second condition of your inner if loop will never be satisfied).
public class HW5 {
public static void main(String[] args) {
String s = "My name is Mathew";
int count = lengthOfLastWord(s);
System.out.println(count);
}
public static int lengthOfLastWord(String s) {
int count = 0;
int countWhite = 0;
char ch;
String reversed = "";
System.out.println("original string is----" + s);
for (int i = s.length() - 1; i >= 0; i--) {
ch = s.charAt(i);
reversed += ch;
}
System.out.println("reversed string is----" + reversed);
for (int i = 0; i < reversed.length(); i++) {
if (!Character.isWhitespace(reversed.charAt(i)))
count++;
if (count > 1 && Character.isWhitespace(reversed.charAt(i)) == true) {
break;
}
}
return count;
}
}
=
and the output is :
original string is----My name is Mathew
reversed string is----wehtaM si eman yM
6
Another way to go about is : you use the inbuilt function split which returns an array of string and then return the count of last string in the array.
I'm trying to write a program which accepts a word in lowercase, converts it into uppercase and changes the vowels in the word to the next alphabet. So far, I've done this:
import java.util.*;
class prg11
{
public static void main(String args[])
{
Scanner sc = new Scanner(System.in);
System.out.println("Enter a word in lowercase.");
String word = sc.next();
word = word.toUpperCase();
int length = word.length();
char ch[] = new char[length+1];
for (int i = 0; i<=length; i++)
{
ch[i] = word.charAt(i);
if("aeiou".indexOf(ch[i]) == 0)
{
ch[i]+=1;
}
}
String str = new String(ch);
System.out.println(str);
}
}
The code compiles fine. But, when I run the program and enter a word, say 'hey', the word is printed in uppercase only. The vowels in it (in this case, 'e'), do not get changed to the next alphabet.
How do I resolve this? TIA.
Need to change three places, according to the code in the question.
word = word.toUpperCase();
int length = word.length();
// yours: char ch[] = new char[length + 1];
// resulting array needs to be as same length as the original word
// if not, there will be array index out of bound issues
char ch[] = new char[length];
// yours: for (int i = 0; i<=length; i++)
// need to go through valid indexes of the array - 0 to length-1
for (int i = 0; i < length; i++) {
ch[i] = word.charAt(i);
// yours: if ("aeiou".indexOf(ch[i]) == 0) {
// two problems when used like that
// 1. indexOf() methods are all case-sensitive
// since you've uppercased your word, need to use AEIOU
// 2. indexOf() returns the index of the given character
// which would be >= 0 when that character exist inside the string
// or -1 if it does not exist
// so need to see if the returned value represents any valid index, not just 0
if ("AEIOU".indexOf(ch[i]) >= 0) {
ch[i] += 1;
}
}
Here's a little concise version. Note the changes I've done.
String word = sc.next().toUpperCase();
char ch[] = word.toCharArray();
for (int i = 0; i < ch.length; i++) {
if ("AEIOU".indexOf(ch[i]) >= 0) {
ch[i] += 1;
}
}
Java doc of indexOf().
public int indexOf(int ch)
Returns the index within this string of the first occurrence of the specified character.
If a character with value ch occurs in the character sequence represented by this String object,
then the index (in Unicode code units) of the first such occurrence is returned.
For values of ch in the range from 0 to 0xFFFF (inclusive), this is the smallest value k such that:
this.charAt(k) == ch
is true. For other values of ch, it is the smallest value k such that:
this.codePointAt(k) == ch
is true. In either case, if no such character occurs in this string, then -1 is returned.
Parameters:
ch - a character (Unicode code point).
Returns:
the index of the first occurrence of the character in the character sequence represented by this object,
or -1 if the character does not occur.
I think this should do it, let me know if it doesn't
public class prg11 {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
System.out.println("Enter a word.");
String word = sc.next();
sc.close();
word = word.toUpperCase();
int length = word.length();
char ch[] = new char[length+1];
for (int i = 0; i<length; i++) {
ch[i] = word.charAt(i);
if("AEIOU".indexOf(ch[i]) > -1) {
ch[i]+=1;
}
}
String str = new String(ch);
System.out.println(str);
}
}
Let me know if it works.
Happy coding ;) -Charlie
Use:
for (int i = 0; i<length; i++)
instead as the last index is length-1.
use for (int i = 0; i<=length-1; i++) instead of for (int i = 0; i<=length; i++) and if("AEIOU".indexOf(ch[i]) != -1) instead of if("aeiou".indexOf(ch[i]) == 0)
reason
1.array index starts from 0 that's why length-1
2. As you already made your string in upper case so check condition on "AEIOU"
3. every non-vowel character will return -1 so use if("AEIOU".indexOf(ch[i]) != -1)
"aeiou".indexOf(ch[i]) == 0 will only match 'a' characters (since that is the character at index 0). You should be looking for any index that is greater than -1. Additionally, since you've already converted the string to uppercase, you should be checking against "AEIOU" instead of "aeiou".
Hey can someone please explain this coding line by line?
public boolean twoE(String str) {
int count = 0;
for (int i=0; i<str.length(); i++) {
if (str.charAt(i) == 'e')
count++;
}
if (count == 2){
return true;
}
return false;
// this last if/else can be written simply as "return (count == 2);"
}
public boolean twoE(String str) {
Declares method twoE that takes the argument str of type String.
int count = 0;
Creates a variable named count of type int and initializes it to 0.
for (int i=0; i<str.length(); i++) {
Uses a for loop to iterate from 0 - the length of the string (str.length()).
if (str.charAt(i) == 'e') count++;
Checks if the the ith letter (str.charAt(i)) of str is a 'e'. If so, increment the count.
if (count == 2) return true;
return false;
If there were 2 'e's, then return true, otherwise, return false.
Note You might not have written this code, but if you did I have one suggestion. Change the last line to return (count == 2); to save space and make the meaning more clear.
The summary of what this function does is that it returns a boolean (true or false) whether or not the String argument passed in contains exactly two lowercase e characters.
How it achieves this is as follows:
Initialize an empty count of 0
Loop through every character of the string
For each character, if the character is a lowercase e, add 1 to the counter
After you are done looping, check what the count was.
If the count was exactly 2, return true, otherwise, return false.
I m working with an array of characters in java. The array can have some missing entries in the middle and I need to know the leftmost index that is empty
My code for that is
private int checkMissingEntry(){
int p = 0;
for(int i = characterArray.length - 1; i >= 0; i--){
if (characterArray[i] == ' '){
p = i;
}
else{
}
}
return p;
}
However, characterArray[i] == ' ' does not detect empty character, the code always returns whatever p was originally assigned to, in this case 0. the if statement never gets executed.
I tried '\0' and '\u0000' but none seems to work.
What is the solution?
private int checkMissingEntry(){
String tmp = new String(characterArray);
if (tmp != null)
return tmp.lastIndexOf(" ");
return -1;
}
Why not search from left to right and return the index immediately when you've reached the first missing character?
EDIT: included example array with missing value
private int checkMissingEntry(){
char[]characterArray = new char[4]; // 4 characters in 1 array
characterArray[0] = 'a'; //but we'll only set values for 3 of them
characterArray[2] = 'b'; //so: index 1 is your empty character
characterArray[3] = 'd';
for(int i = 0; i < characterArray.length ; i++){
char c = characterArray[i]; //get the character at index i
if(c =='\0' || c =='\u0000'){ //check for empty character
return i; //return index
}
} return -1; //only returns -1 if characterArray does not contain the empty character
}
I'm working with the following:
private char [][] board;
<various lines of code>
//Sequential searching for an index that has yet to be
//changed from the default char character
for(int i = 0; i< board.length; i++)
{
for(int j = 0; j>board[i].length; j++)
{
//Here I get the error "incomparable types: char and char[]
if('\u0000' == board[j])
System.out.println("Game unfinished.");
}
//Here I get the error "incomparable types: char and char[]
if('\u0000' == board[j])
System.out.println("Game unfinished.");
}
else return 'T';
In essence, I want to traverse the array, doing either one of two things:
If all array indexes are occupied by either 'X' or 'O' then return 'T' OR
If an array index is found with '\u0000' do:
System.out.print("Game unfinished.");
First, you'll want to add a null check, just in case. Then, fix the for condition as #libik indicated. Finally, reference the cell by its i and j indecies. e.g:
for(int i = 0; i < board.length; i++) {
//Always check for nulls, unless you're 100% certain of the data
if (board[i] != null) {
for(int j = 0; j < board[i][j].length; j++) {
//Here I get the error "incomparable types: char and char[]
if('\u0000' == board[i][j]) {
System.out.println("Game unfinished.");
}
}
}
Regarding the second if statement and the return 'T', these don't make sense as they stand. Did you want to return 'T' if no '\u0000' chars where found in the array? If so, create a boolean flag, initialize it to false, then set it on the else condition of the if statement above. Outside of the loop, add a second if to see if the flag was ever set and return 'T'.
You have two mistakes.
First change j>board[i].length to j<board[i].length
Then you have to compare char to char, in 2D char, you have to specify both dimension, to get char, specify only one means you only specify row or column of chars (thus it is array of char).
Comparing should look like this : if('\u0000' == board[i][j])