The Goat Latin problem asks you to convert a given sentence into a made-up language called "Goat Latin" by following specific rules for each word in the sentence.
sentence
containing English words separated by spaces.a, e, i, o, u
, case-insensitive), append "ma"
to the end of the word."ma"
.'a'
to the end of each word per its word index in the sentence, starting with 1 (i.e., the first word gets "a", the second gets "aa", etc.).Constraints:
sentence
.To solve this problem, we need to process each word in the input sentence and apply a series of string manipulations based on its first letter. At first glance, one might consider iterating through the sentence character by character, but since the rules apply on a per-word basis, it makes sense to split the sentence into words.
For each word, we need to:
The problem is straightforward and does not require complex data structures. However, attention to detail is important to correctly implement each rule, especially the handling of word indices and the case-insensitive check for vowels.
Let's break down the solution step by step:
This approach is efficient because string operations on individual words are fast, and we only traverse the list of words once. No extra data structures are needed beyond a list for the result.
Let's walk through an example with the input: "I speak Goat Latin"
.
"Imaa peaksmaaa oatGmaaaa atinLmaaaaa"
Brute-force Approach: Even a naive approach that processes each word one by one has time complexity O(N), where N is the total number of characters in the sentence. Each word is processed in O(1) time relative to its length, and the number of words is at most N.
Optimized Approach: The described approach also runs in O(N) time, as each character is visited a constant number of times (splitting, processing, and joining). Space complexity is O(N) as we store the transformed words in a list before joining.
The Goat Latin problem is a straightforward string manipulation exercise. By splitting the sentence into words and applying the rules for vowels, consonants, and suffixes, we can efficiently transform the sentence. The solution is elegant because it leverages language features for string processing and cleanly separates each rule into a step, resulting in clear and maintainable code.
class Solution:
def toGoatLatin(self, sentence: str) -> str:
vowels = set('aeiouAEIOU')
words = sentence.split()
result = []
for i, word in enumerate(words):
if word[0] in vowels:
goat_word = word + 'ma'
else:
goat_word = word[1:] + word[0] + 'ma'
goat_word += 'a' * (i + 1)
result.append(goat_word)
return ' '.join(result)
class Solution {
public:
string toGoatLatin(string sentence) {
unordered_set<char> vowels = {'a','e','i','o','u','A','E','I','O','U'};
vector<string> words;
stringstream ss(sentence);
string word, result;
int index = 1;
while (ss >> word) {
if (vowels.count(word[0])) {
word += "ma";
} else {
word = word.substr(1) + word[0] + "ma";
}
word += string(index, 'a');
if (!result.empty()) result += ' ';
result += word;
++index;
}
return result;
}
};
class Solution {
public String toGoatLatin(String sentence) {
String[] words = sentence.split(" ");
StringBuilder sb = new StringBuilder();
String vowels = "aeiouAEIOU";
for (int i = 0; i < words.length; i++) {
String word = words[i];
if (vowels.indexOf(word.charAt(0)) != -1) {
sb.append(word);
} else {
sb.append(word.substring(1));
sb.append(word.charAt(0));
}
sb.append("ma");
for (int j = 0; j <= i; j++) {
sb.append('a');
}
if (i != words.length - 1) sb.append(' ');
}
return sb.toString();
}
}
/**
* @param {string} sentence
* @return {string}
*/
var toGoatLatin = function(sentence) {
const vowels = new Set(['a','e','i','o','u','A','E','I','O','U']);
return sentence.split(' ').map((word, i) => {
let goatWord = '';
if (vowels.has(word[0])) {
goatWord = word + 'ma';
} else {
goatWord = word.slice(1) + word[0] + 'ma';
}
goatWord += 'a'.repeat(i + 1);
return goatWord;
}).join(' ');
};