I'm a Staff Software Engineer at Cisco. I specialize in Python and Go, building functional, practical, and maintainable web systems leveraging Kubernetes and the cloud. Blog opinions are my own.
Do you have the big long string of text? You've got me hooked and I want to solve it, but it seems like it would be more fun to actually get the secret word at the end :)
Not sure why, but my paste of the long string in this comment did not come in correctly as was mentioned below. You can find it on repl.it at repl.it/MivX.
I'm a Staff Software Engineer at Cisco. I specialize in Python and Go, building functional, practical, and maintainable web systems leveraging Kubernetes and the cloud. Blog opinions are my own.
Your solution in Ruby is awesome. I also love the dedication to benchmarking your two different variations and very interesting results on .count and it's optimization. I didn't know that before. Overall, Ruby is just plain awesome.
I'm a Staff Software Engineer at Cisco. I specialize in Python and Go, building functional, practical, and maintainable web systems leveraging Kubernetes and the cloud. Blog opinions are my own.
Running against the blob above it seems the answer is a word followed by some misc character (the last 4 almost spelling out an f-bomb). Did I get the right answer or is something off? I did a codepen with your code and it seems to give the same answer.
from collections import Counter
with open('test.input') as fd: # the string is in the "test.input" file
c = Counter(fd.read())
string = ''.join(sorted(c.keys(), key=lambda x: -1 * c[x]))
print(string[:string.index('_')])
@benhayehudi
this is a great write-up. Really highlights the way you approached and then solved the problem. As a Javascript novice myself, I appreciated the step-by-step explanation of the decisions you made.
How did this coding challenge compare to others you've taken?
This coding challenge ranked as a bit more involved for an initial challenge, i.e. as a requirement for inclusion with a resume submission and not something to do after an initial phone screen. I think it's actually a smart way for a place to be more upfront about their needs and skills required before taking up too much time of the people interested and their own time.
I'm a Staff Software Engineer at Cisco. I specialize in Python and Go, building functional, practical, and maintainable web systems leveraging Kubernetes and the cloud. Blog opinions are my own.
You don't necessarily have to loop through and initialize each key for strngs manually. Here's a couple of alternatives.
# Your versionstrngs={}forcharininitchar:strngs[char]=0# you can create a dict out of a sequence of keys and starting value# credit: @edh_developerstrngs=dict.fromkeys(initchar,0)# you can also use a defaultdict, which creates the key with a default value# if it doesn't find the key there on accessfromcollectionsimportdefaultdictstrngs=defaultdict(int)# defaults to zero
You can use shorthand notation if you're modifying a value inplace.
# Your versionstrngs[char]=strngs[char]+1# shortcutstrngs[char]+=1
You can use dict.items to get a list of pairs out of a dict that is much easier to sort. Then you don't have to manually sort and delete items out of your dict.
# Your versionwhile(strngs!={}):maximum=max(strngs,key=strngs.get)word=word+maximumdelstrngs[maximum]# Could bepairs=strngs.items()desc=sorted(pairs,key=lambdax:x[1])# the key= argument lets us# sort by the second itemdesc_letters=''.join(x[0]forxindesc)# Grab the first value (letter) from each pair
In general, when you're building a string, it's usually more performant, easier, and less error prone to build the whole thing as a list and join it at the end.
# Instead of this:word=""foriteminthings:word=word+complicated_process(item)# Since strings are immutable, this forces you to throw away# your old string and create a new one *each time* which is expensive# More efficient:word=[]foriteminthings:word.append(complicated_process(item))letters=''.join(word)# Use list comprehensions (see link below) for even faster,# cleaner, more pythonic code :)word=[complicated_process(item)foriteminthings]letters=''.join(word)# Use a generator expression (like above) for *even better* results!letters=''.join(complicated_process(item)foriteminthings)
Do you have the big long string of text? You've got me hooked and I want to solve it, but it seems like it would be more fun to actually get the secret word at the end :)
Hey Ryan,
Not sure why, but my paste of the long string in this comment did not come in correctly as was mentioned below. You can find it on repl.it at repl.it/MivX.
Enjoy! :)
Ben
Victory! I found an interesting performance quirk, at least for Ruby. Thanks for a great puzzle and write-up!
Your solution in Ruby is awesome. I also love the dedication to benchmarking your two different variations and very interesting results on
.countand it's optimization. I didn't know that before. Overall, Ruby is just plain awesome.Thanks! Yeah, I was super sure the way you did it would be faster. Ruby is one of my favorite things!
Running against the blob above it seems the answer is a word followed by some misc character (the last 4 almost spelling out an f-bomb). Did I get the right answer or is something off? I did a codepen with your code and it seems to give the same answer.
My solution. In python.
Probably not the most elegant way... I really need more practice with Rust :D
@benhayehudi this is a great write-up. Really highlights the way you approached and then solved the problem. As a Javascript novice myself, I appreciated the step-by-step explanation of the decisions you made.
How did this coding challenge compare to others you've taken?
Thanks Peter!
This coding challenge ranked as a bit more involved for an initial challenge, i.e. as a requirement for inclusion with a resume submission and not something to do after an initial phone screen. I think it's actually a smart way for a place to be more upfront about their needs and skills required before taking up too much time of the people interested and their own time.
Great Post! Thanks!
My C# approach would be something like this:
The problem with fast shooting, is always the same, mistakes! :/
Hey!
Can someone check my python solution? Any hints where/how can the code be better?
repl.it/Mnem/0
TY
Hi! A couple of notes that you can take or leave.
You don't necessarily have to loop through and initialize each key for
strngsmanually. Here's a couple of alternatives.You can use shorthand notation if you're modifying a value inplace.
You can use
dict.itemsto get a list of pairs out of a dict that is much easier to sort. Then you don't have to manually sort and delete items out of your dict.Some things to look up here for more information:
In general, when you're building a string, it's usually more performant, easier, and less error prone to build the whole thing as a list and
joinit at the end.Here's a link on list comprehensions
Hopefully this helps. I'm not sure how comfortable you are with Python, so I tried to cover everything. Let me know if you have any questions 😁
Here's a py3 version using the builtin dict and iterators:
from operator import itemgetterlong_string = "..."counter = dict()for c in iter(long_string):counter[c] = counter.get(c, 0) + 1sorted_chars = [k for (k, v) in sorted(counter.items(), key=itemgetter(1), reverse=True)]word = "".join(sorted_chars[:sorted_chars.index('_')] )print(word)