This is what I'm trying to do. I have some text and I'm trying to filter through it and only print out the TOP TEN words with the most vowels. This is only a portion of my code, but this is the only part that I keep getting an error on. The error I get is: unorderable types NoneType() < int()....and I get that error when i try and sort my words. (let me know if I am unclear or confusing) How can I fix this error (in my topTen function)? This is the little piece of code I'm talking about:
def topTen(text):
words = textToWords(text)
words.sort(key=countVowels, reverse=True)
for ctr in range(10):
print(words[ctr])
def textToWords(T):
W = []
for line in T:
words = line.split()
for word in words:
W.append(word.lower())
return W
def countVowels(st):
ctr = 0
for ch in st:
if ch in "aeiou":
ctr =+ 1
return ctr
The last line of countVowels is not indented correctly. When the if statement is taken the function will return 1; when the if statement is never taken (the word contains no vowels) the function returns None. Re-indent the return ctr so it's outside the loop and I think the program will work.
Related
There is such a task with Leetcode. Everything works for me when I press RUN, but when I submit, it gives an error:
text = "a b c d e"
brokenLetters = "abcde"
Output : 1
Expected: 0
def canBeTypedWords(self, text, brokenLetters):
for i in brokenLetters:
cnt = 0
text = text.split()
s1 = text[0]
s2 = text[1]
if i in s1 and i in s2:
return 0
else:
cnt += 1
return cnt
Can you please assist what I missed here?
Everything work exclude separate letters condition in a text.
So consider logically what you have to do, then write that algorithmically.
Logically, you have a list of words, a list of broken letters, and you need to return the count of words that have none of those broken letters in them.
"None of those broken letters in them" is the important bit -- if even one broken letter is in the word, it's no good.
def count_words(broken_letters, word_list) -> int:
words = word_list.split() # split on spaces
broken_letters = set(broken_letters) # we'll be doing membership checks
# on this kind of a lot, so changing
# it to a set is more performant
count = 0
for word in words:
for letter in word:
if letter in broken_letters:
# this word doesn't work, so break out of the
# "for letter in word" loop
break
else:
# a for..else block is only entered if execution
# falls off the bottom naturally, so in this case
# the word works!
count += 1
return count
This can, of course, be written much more concisely and (one might argue) idiomatically, but it is less obvious to a novice how this code works. As exercise to the reader: see if you can understand how this code works and how you might modify it if the exercise was, instead, giving you all the letters that work rather than the letters that are broken.
def count_words(broken_letters, word_list) -> int:
words = word_list.split()
broken_letters = set(broken_letters)
return sum((1 for word in words if all(lett not in broken_letters for lett in word)))
So i was solving a question that is in my Lab practical Syllabus. Below is the question:-
Write a python class to reverse a sentence (initialized via
constructor) word by word. Example: “I am here” should be reversed as
“here am I”. Create instances of this class for each of the three
strings input by the user and display the reversed string for each, in
descending order of number of vowels in the string.
Below is code for the implementation of above question:-
class sentenceReverser:
vowels = ['a','e','i','o','u']
vowelCount =0
sentence=""
reversed_string = ""
def __init__(self,sentence):
self.sentence = sentence
self.reverser()
def reverser(self):
self.reversed_string = " ".join(reversed(self.sentence.split()))
return self.reversed_string
def getVowelCount(self):
for i in self.sentence:
if i.lower() in self.vowels:
self.vowelCount += 1
return self.vowelCount
inp = []
for i in range(2):
temp = input("Enter string:- ")
ob = sentenceReverser(temp)
inp.append(ob)
sorted_item = sorted(inp,key = lambda inp:inp.getVowelCount(),reverse=True)
for i in range (len(sorted_item)):
print('Reversed String: ',sorted_item[i].reverser(),'Vowel count: ',sorted_item[i].getVowelCount())
Below is output i am getting for the above code:-
issue:-
Could someone tell me why i am getting double the vowel count???
Any help would be appreciated!!
You are calling getVowelCount() twice. Instead you can use the variable instead of calling in the print command
for i in range (len(sorted_item)):
print('Reversed String: ',sorted_item[i].reverser(),'Vowel count: ',sorted_item[i].vowelCount)
This is because you don't reset vowel count in the method. So if you execute the method once (here in sort), you'll get correct count. If you execute it twice (in printing), you will get twice as much. If you execute it once more, you'll get 3x correct amount. And so on.
The solution is to reset the number:
def getVowelCount(self):
self.vowelCount = 0
for i in self.sentence:
if i.lower() in self.vowels:
self.vowelCount += 1
return self.vowelCount
Or to calculate it only once - set it to None, then calculate only if self.vowelCount is None, otherwise return existing value.
I'm taking the MIT DS&A algorithm course and on the document distance problem, we have to parse a file into a list of words, then count the frequency of each word in the file. I have a hard time comprehending the following function:
def count_frequency(word_list):
"""
Return a list giving pairs of form: (word,frequency)
"""
L = []
for new_word in word_list:
for entry in L:
if new_word == entry[0]:
entry[1] = entry[1] + 1
break
else:
L.append([new_word,1])
return L
Why do we compare new_word to entry[0]?
a. What if L is empty? What do we compare new_word to?
b. Why do we compare new_word to entry[0] specifically? Why don't we do something like
if new_word in L
c. Why do we need to use break?
Why is the else block 1 tab to the right of the earlier if block? When I tried to indent the else block, an indentation error would show up.
Thank you for your help!
The list L contains two-item entries due to L.append([new_word,1]). If L is empty the for would not be entered, so there is no problem with entry[0].
entry[0] is a word and entry[1] is a count. You can't say if new_word in L because it is not just a list of strings.
break stops the for once a word is found.
for/else is a thing in Python. The else runs if the for completes without interruption (a break in this case). If new_word isn't in L, the for won't break and the new word and a count of 1 is added to L.
FYI, the built-in collections.Counter() would return similar results.
I am completing this HackerRank coding challenge. Essentially, the challenge asks us to find all the substrings of the input string without mixing up the letters. Then, we count the number of substrings that start with a vowel and count the number of substrings that start with a consonant.
The coding challenge is structured as a game where Stuart's score is the number of consonant starting substrings and Kevin's score is the number of vowel starting substrings. The program outputs the winner, i.e. the one with the most substrings.
For example, I created the following code:
def constwordfinder(word):
word = word.lower()
return_lst = []
for indx in range(1,len(word)+1):
if word[indx-1:indx] not in ['a','e','i','o','u']:
itr = indx
while itr < len(word)+1:
return_lst.append(word[indx-1:itr])
itr +=1
return return_lst
def vowelwordfinder(word):
word = word.lower()
return_lst = []
for indx in range(1,len(word)+1):
if word[indx-1:indx] in ['a','e','i','o','u']:
itr = indx
while itr < len(word)+1:
return_lst.append(word[indx-1:itr])
itr +=1
return return_lst
def game_scorer(const_list, vow_list):
if len(const_list) == len(vow_list):
return 'Draw'
else:
if len(const_list) > len(vow_list):
return 'Stuart ' + str(len(const_list))
else:
return 'Kevin ' + str(len(vow_list))
input_str = input()
print(game_scorer(constwordfinder(input_str), vowelwordfinder(input_str)))
This worked for smaller strings like BANANA, although when HackerRank started inputting strings like the following, I got multiple Runtime errors on the test cases:
NANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANANNANAN
I tried structuring the program to be a bit more concise, although I still got Runtime errors on the longer test cases:
def wordfinder(word):
word = word.lower()
return_lst = []
for indx in range(1,len(word)+1):
itr = indx
while itr < len(word)+1:
return_lst.append(word[indx-1:itr])
itr +=1
return return_lst
def game_scorer2(word_list):
kevin_score = 0
stuart_score = 0
for word in word_list:
if word[0:1] not in ['a','e','i','o','u']:
stuart_score += 1
else:
kevin_score +=1
if stuart_score == kevin_score:
return 'Draw'
else:
if stuart_score > kevin_score:
return 'Stuart ' + str(stuart_score)
else:
return 'Kevin ' + str(kevin_score)
print(game_scorer2(wordfinder(input())))
What else exactly should I be doing to structure my program to avoid Runtime errors like before?
Here's a quick and dirty partial solution based on my hints:
input_str = raw_input()
kevin = 0
for i, c in enumerate(input_str):
if c.lower() in "aeiou":
kevin += len(input_str) - i
print kevin
Basically, iterate over each character, and if it is in the set of vowels, Kevin's score increases by the number of remaining characters in the string.
The remaining work should be rather obvious, I hope!
[stolen from the spoilers section of the site in question]
Because say for each consonant, you can make n substrings beginning with that consanant. So for the BANANA example look at the first B. With that B, you can make: B, BA, BAN, BANA, BANAN, BANANA. That's six substrings starting with that B or length(string) - indexof(character), which means that B adds 6 to the score. So you go through the string, looking for each consonant, and add length(string) - index to the score.
The problem here is your algorithm.You are finding all the Sub strings of the text. It takes exponential time to solve the problem. That's why you got run time errors here. You have to use another good algorithm to solve this problem rather than using sub strings.
Working on a very common problem to identify whether word is abecedarian (all letters in alphabetical order). I can do one word in several ways as discovered in "Think Python"; but, would like to be able to iterate through a list of words determining which are abecedarian and counting those that are.
def start():
lines= []
words= []
for line in open('word_test1.txt'):
lines.append(line.strip())
numlines=len(lines)
count = 0
for word in lines[:]:
i = 0
while i < len(word)-1:
if word[i+1] < word[i]:
return
i = i+1
print (word)
count= count + 1
print (count)
start()
I think my problem lies with the "return" in the "while i" loop. In the list I'm using there are at least three abecedarian words. The above code reads the first two (which are the first entries), prints them, counts them but on the following non-abecedarian word breaks out of the loop and ends the program.
I'm new at programming and this has taken me several hours over a couple of days.
No need for low level programming on this one :-)
def is_abcedarian(s):
'Determine whether the characters are in alphabetical order'
return list(s) == sorted(s)
The use filter to run over a list of words:
>>> filter(is_abcedarian, ['apple', 'bee', 'amp', 'sun'])
['bee', 'amp']
The return statement is breaking out of the entire start() function. There are many possible ways to solve this, but the clearest might be to break your code into two functions like this:
def is_abcedarian(word):
i = 0
while i < len(word)-1:
if word[i+1] < word[i]:
return False
i = i+1
return True
def start():
lines= []
words= []
for line in open('word_test1.txt'):
lines.append(line.strip())
numlines=len(lines)
count = 0
for word in lines[:]:
if is_abcedearian(word):
print (word)
count= count + 1
print (count)
In this example, the return statements in is_abcedarian() returns only from that function, and the return value is then tested by the if statement inside the for loop.
Once you have split apart your program in this way, you have the added benefit of being able to use your is_abcedarian() function from other places (in future related code you might write).
I believe you intended to break from the while loop when you find the letter's are not in order and instead you issued the return statement, which returns you from the function start.
There could be couple of ways to do this
You can use Exception, to raise a StopIteration Exception and catch it outside the while loop.
for word in lines[:]:
try:
i = 0
while i < len(word)-1:
if word[i+1] < word[i]:
raise StopIteration
i = i+1
print (word)
except StopIteration:
None
You can also try setting a flag found and then use it later to test for printing the word
A slightly reorganized approach:
def is_abcedarian(word):
return sorted(s)==list(s)
def main():
# read input file
with open('word_test1.txt') as inf:
words = [line.strip() for line in inf]
# figure out which words are "good"
good_words = [word for word in words if is_abcedarian(word)]
# print the "good" words
print("\n".join(good_words))
print(len(good_words))
if __name__=="__main__":
main()
I like iterools:
from itertools import tee, izip
def pairwise(iterable):
a, b = tee(iterable)
next(b)
return izip(a, b)
def is_abcdarien(word):
return all(c < d for c, d in pairwise(word))
words = 'asdf', 'qwer', 'fghi', 'klmn', 'aabcd', 'abcd'
print filter(is_abcdarien, words)
print len(filter(is_abcdarien, words))
Result:
('fghi', 'klmn', 'abcd')
3
Change c < d to c <= d if you want non-strict ordering, so that "aabcd" is also abcdarian, .
I have this solution for you - I have found it in the same place as you. I hope it still helps.
def is_abecedarian(word):
word.lower()
letter_value=0
for letter in word:
if ord(letter) < letter_value:
return False
else:
letter_value = ord(letter)
return True
fin = open('words.txt')
words_no = 0
for line in fin:
word = line.strip()
if is_abecedarian(word):
words_no = words_no + 1
print words_no