Here is what I'm trying to do:
I want to count letters frequency in a sentence.
Here is my code in python so far:
for i in line:
if i in my_count.keys():
my_count[i]+=1
else:
my_count[i]=1
Is there any way to fulfill the same goal with dict comprehension, the same we would do with list comprehension?
I have thought at something such as :
my_count = { x:(my_count[x]+=1) for x in line if x in my_count else x:1 }
But this does not pass the syntax check (SyntaxError: invalid syntax at the +=).
Thanks for your help and advices!
Counter in collections seems to accomplish this.
In [1]: line = 'the quick brown fox jumps over the lazy dog'
In [2]: from collections import Counter
In [3]: c = Counter(line)
In [4]: c
Out[4]: Counter({' ': 8, 'o': 4, 'e': 3, 'h': 2, 'r': 2, 'u': 2, 't': 2, 'a': 1, 'c': 1, 'b': 1, 'd': 1, 'g': 1, 'f': 1, 'i': 1, 'k': 1, 'j': 1, 'm': 1, 'l': 1, 'n': 1, 'q': 1, 'p': 1, 's': 1, 'w': 1, 'v': 1, 'y': 1, 'x': 1, 'z': 1})
Related
I have two Dictionaries resources, and available_resources:
resources = {'B': 1, 's': 2, 't': 3, 'e': 3, '!': 1, 'h': 1, 'i': 1, ' ': 3, 'o': 1, 'g': 1, 'E': 1, 'A': 1, 'x': 2, 'p': 1, 'l': 1, 'r': 1}
available_resources = {'A': 1, 'l': 1, 'g': 1, 'o': 1, 'E': 1, 'x': 1, 'p': 1, 'e': 3, 'r': 1, 't': 3, ' ': 3, 'i': 1, 's': 2, 'h': 1, 'B': 1, '!': 1}
I want to check if resources is a subset of available_resources (if each element contained in the dictionary is <= the corresponding value entry in the resources dictionary)
I've tried:
if all(available_resources.get(key, None) == val for key, val
in resources.items()):
return True
It is returning false, is there another way I can get it to work?
Could it be a simple sign error? From "==" val to "<=" val? I got true from the below.
if all(available_resources.get(key, None) <= val for key, val
in resources.items()):
return True
If all the values are integers, one approach is to use collections.Counter:
from collections import Counter
resources = {'B': 1, 's': 2, 't': 3, 'e': 3, '!': 1, 'h': 1, 'i': 1, ' ': 3, 'o': 1, 'g': 1, 'E': 1, 'A': 1, 'x': 2, 'p': 1, 'l': 1, 'r': 1}
available_resources = {'A': 1, 'l': 1, 'g': 1, 'o': 1, 'E': 1, 'x': 1, 'p': 1, 'e': 3, 'r': 1, 't': 3, ' ': 3, 'i': 1, 's': 2, 'h': 1, 'B': 1, '!': 1}
res = bool(Counter(resources) - Counter(available_resources))
print(res)
Output
True
You can use the <= operator from sets. This operator determines whether one set is a subset of the other.
As follows:
>>> resources.items() <= available_resources.items()
False
This returns False as there is a difference between the element x in the different dict. You can see this difference using the set operator ^ with will return you the symmetric difference between the dict:
>>> resources.items() ^ available_resources.items()
{('x', 1), ('x', 2)}
You need to use <= instead of ==
>>> all(available_resources.get(k, -1)<=v for k,v in resources.items())
True
Also, above method may fail if resources contains some key that doesn't exist in available_resources, and you can additionally check if the keys in resources are subset of the keys in available_resources for this condition
>>> all(available_resources.get(k, -1)<=v for k,v in resources.items()) and\
set(resources).issubset(available_resources)
True
I have tested the answers in this stackoverflow question: click here
And i think it's works for you!
all(item in available_resources.items() for item in resources.items())
# - or - #
available_resources.items() <= resources.items()
def count_letters(text):
result = {}
# Go through eactter in the text
for letter in text:
# Check if the letter needs to be counted or not
if letter in text:
result[letter.lower()]=result.get(letter,0)+1
# Add or increment the value in the dictionary
for k in result:
return result
print(count_letters("AaBbCc"))
# Should be {'a': 2, 'b': 2, 'c': 2}
print(count_letters("Math is fun! 2+2=4"))
# Should be {'m': 1, 'a': 1, 't': 1, 'h': 1, 'i': 1, 's': 1, 'f': 1, 'u': 1, 'n': 1}
print(count_letters("This is a sentence."))
# Should be {'t': 2, 'h': 1, 'i': 2, 's': 3, 'a': 1, 'e': 3, 'n': 2, 'c': 1}
You can use Counter with filter.
import string
from collections import Counter
Counter(filter(lambda x:x in string.ascii_letters,_str.lower()))
Counter({'m': 1,
'a': 1,
't': 1,
'h': 1,
'i': 1,
's': 1,
'f': 1,
'u': 1,
'n': 1})
Say I have a dictionary like this,
SCRABBLE_LETTER_VALUES = {
'a': 1, 'b': 3, 'c': 3, 'd': 2, 'e': 1, 'f': 4, 'g': 2, 'h': 4, 'i': 1, 'j': 8, 'k': 5, 'l': 1, 'm': 3, 'n': 1, 'o': 1, 'p': 3, 'q': 10, 'r': 1, 's': 1, 't': 1, 'u': 1, 'v': 4, 'w': 4, 'x': 8, 'y': 4, 'z': 10
}
Now, say I have a variable like this.
letter = 'i'
I want to add the corresponding value to the variable score. So since letter is equal to i, then score should equal 1
SCRABBLE_LETTER_VALUES = {'a': 1, 'c': 3, 'b': 3, 'e': 1, 'd': 2, 'g': 2, 'f': 4, 'i': 1, 'h': 4, 'k': 5, 'j': 8, 'm': 3, 'l': 1, 'o': 1, 'n': 1, 'q': 10, 'p': 3, 's': 1, 'r': 1, 'u': 1, 't': 1, 'w': 4, 'v': 4, 'y': 4, 'x': 8, 'z': 10}
>>> SCRABBLE_LETTER_VALUES['i']
1
>>> SCRABBLE_LETTER_VALUES['z']
10
Dictionary values are accessed using dictionary_name[key]. So in this case:
score+=SCRABBLE_LETTER_VALUES[letter]
You also need to assign score to something before you do this:
score=0
You might find it useful to read the documentation on dictionaries: https://docs.python.org/3/tutorial/datastructures.html#dictionaries
Firstly you need to know how python plays with dictionary- the question you asked in very simple thus people are downvoting!
Answering you question:
You have the following code in mind and struggling for the rest. I will be answering them accordingly under your statements.
SCRABBLE_LETTER_VALUES = {
'a': 1, 'b': 3, 'c': 3, 'd': 2, 'e': 1, 'f': 4, 'g': 2, 'h': 4, 'i': 1, 'j': 8, 'k': 5, 'l': 1, 'm': 3, 'n': 1, 'o': 1, 'p': 3, 'q': 10, 'r': 1, 's': 1, 't': 1, 'u': 1, 'v': 4, 'w': 4, 'x': 8, 'y': 4, 'z': 10
}
letter = 'i'
In python to get value for a corresponding key it work like dictionary[key], which gives the output.
So for your problem if we do SCRABBLE_LETTER_VALUES[letter], its the same as doing SCRABBLE_LETTER_VALUES['i'] where 'i' is the key and we will get 1 as output.
Hence for SCRABBLE_LETTER_VALUES[letter] we get 1 as output!
I want to add the corresponding value to the variable score. So since letter is equal to i
Assigning the corresponding value to the variable score is score = SCRABBLE_LETTER_VALUES[letter]
then score should equal 1
and we know now for sure that the value of score is 1. Don't we?
For SCRABBLE_LETTER_VALUES[letter] value is 1 when letter= 'i' thus score is 1
I'm trying to create a histogram function that takes strings and counts the number of times the strings was used and put into a dictionary. I'm still learning Python so any tips would be helpful.
>>> histogram('The Goose that Laid the Golden Egg')
{'l': 2, 'n': 1, 'o': 3, 'h': 3, 'i': 1,'d': 2, 'e': 5, 'g': 4, ' ': 6, 'a': 2, 't': 4, 's': 1}
Its what that collections.Counter is for :
>>> from collections import Counter
>>> Counter('The Goose that Laid the Golden Egg')
Counter({' ': 6, 'e': 4, 'h': 3, 'o': 3, 't': 3, 'a': 2, 'd': 2, 'G': 2, 'g': 2, 'i': 1, 'L': 1, 'l': 1, 's': 1, 'T': 1, 'E': 1, 'n': 1})
I won't solve this for you, but will give you a hint: use collections.Counter. Combine this with the fact that strings are iterable, and this gets you very close to a solution.
Write a Python function called LetterCount() which takes a string as an argument and returns a dictionary of letter counts.
The line:
print LetterCount("Abracadabra, Monsignor")
Should produce the output:
{'a': 5, 'c': 1, 'b': 2, 'd': 1, 'g': 1, 'i': 1, 'm': 1, 'o': 2, 'n': 2, 's': 1, 'r': 3}
I tried:
import collections
c = collections.Counter('Abracadabra, Monsignor')
print c
print list(c.elements())
the answer I am getting looks like this
{'a': 4, 'r': 3, 'b': 2, 'o': 2, 'n': 2, 'A': 1, 'c: 1, 'd': 1, 'g': 1, ' ':1, 'i':1, 'M':1 ',':1's': 1, }
['A', 'a','a','a','a','c','b','b','d','g', and so on
okay now with this code
import collections
c = collections.Counter('Abracadabra, Monsignor'.lower())
print c
am getting this
{'a': 5, 'r': 3, 'b': 2, 'o': 2, 'n': 2, 'c: 1, 'd': 1, 'g': 1, ' ':1, 'i':1, ',':1's': 1, }
but answer should be this
{'a': 5, 'c': 1, 'b': 2, 'd': 1, 'g': 1, 'i': 1, 'm': 1, 'o': 2, 'n': 2, 's': 1, 'r': 3}
You are close. Note that in the task description, the case of the letters is not taken into account. They want {'a': 5}, where you have {'a': 4, 'A': 1}.
So you have to convert the string to lower case first (I'm sure you will find out how).
Use dictionary for the letter count:
s = "string is an immutable object"
d = {}
for i in s:
d[i] = d.get(i,0)+1
print d
Output:
{'a': 2, ' ': 4, 'c': 1, 'b': 2, 'e': 2, 'g': 1, 'i': 3, 'j': 1, 'm': 2, 'l': 1, 'o': 1, 'n': 2, 's': 2, 'r': 1, 'u': 1, 't': 3}
Maybe this to count just letters, exclude spaces and overlook its case and sort them alphabetically?:
t = "The cat is out of the bag."
word_count = {}
for i in t.casefold():
if i.isalnum():
word_count[i] = word_count.get(i,0)+1
for letter, count in sorted(word_count.items()):
print(letter, count)
Output:
a 2
b 1
c 1
e 2
f 1
g 1
h 2
i 1
o 2
s 1
t 4
u 1