All possible combinations add of letters - python

I greet you all I need help I have this code here
how can i achieve this if I want letters to be added between the letters
example
input
east
output
aeast
eaast
eaast
easat
easta
aeast
beast
ebast
eabst
easbt
eastb
ect...
leters = 'abcdefghijklmnopqrstuvwxyz'
words = ('east')
for letersinput in leters:
for rang in range(1):
print(letersinput+""+str(words)+"")
I'm looking for the exact opposite of this, how to do it?
def missing_char(word, n):
n = abs(n)
front = word[:n]
back = word[n+1:]
return front + back

Iterate through the words and letters, and for each position, slice the word at the position and insert the letter:
letters = 'abcdefghijklmnopqrstuvwxyz'
words = ['east']
for word in words:
for letter in letters:
for i in range(len(word)+1):
print(word[:i] + letter + word[i:])
print()
Output:
aeast
eaast
eaast
easat
easta
beast
ebast
eabst
easbt
eastb
...
zeast
ezast
eazst
easzt
eastz

Related

How to shuffle letters in string with vowel isolated in Python

I am creating a function
Takes input as a string.
Returns a string.
The return string will have the same number of words as the input string, and the same letters as the input string, but the individual words can be of different length. i.e.
perm_lets("try this") == "ist thry"
is a valid return-value. By "number of words" in a string X, we mean the length of the list X.split(' '), i.e. one more than the number of blank spaces in the string. A "word" means a string of letters with no spaces. Lastly,
Every vowel must be isolated, i.e. immediately beside vowels you have at most spaces and/or consonants.
My function can only shuffle the letters of the input string. I would like to know how to isolate the vowel
import random as rd
def perm_lets(input_string):
nS = ''.join(rd.sample(input_string,len(input_string)))
print(nS)
I expect the output of perm_lets("this is a loop") to be something like "si olo pit ahs" but the actual output is " ph siioaos lt" (spaces in the wrong place and vowels are not isolated).
Brute force randomization with disqualifying tests:
import re
import random
import time
def perm_lets(s):
s = list(s)
start = time.perf_counter()
while True:
random.shuffle(s)
p = ''.join(s)
if ' ' in p: continue # no spaces together
if p.startswith(' ') or p.endswith(' '): continue # don't start or end with space
if re.search(r'[aeiou]{2}',p): continue # no vowels together
elapsed = time.perf_counter() - start
return p,elapsed
print(perm_lets('this is a loop'))
print(perm_lets('i bid you adieu'))
Output (4 runs):
('sopihats o i l', 0.0009378000000026532)
('ade udo ibiyi u', 0.07766600000000068)
('i o ha tpsislo', 0.00026450000000011187)
('o adebudu iyi i', 0.00632540000000148)
('o la sstipi ho', 5.2900000000022374e-05)
('udobida eyi i u', 0.3843909999999937) # 1/3 of a second for a tough sentence
('ipa hts o soli', 0.00028810000000589753)
('idida e obu uyi', 0.18083439999999484)
Note: "adieu louie" has no solution.
Here is one way to attempt what you are after. Separates vowels from consonants, shuffles them for randomness, zips vowels and consonants in a poor attempt to isolate the vowels (but this will fail if there are too many more vowels than consonants), randomly selects word length ensuring minimum of one character per word and that the number of output words is the same as the number of input words.
You could probably do a better job isolating vowels by generating more single vowel words when necessary. However, depending on the vowel to consonant ratio and the number of words, there will always be scenarios where you can't both isolate vowels and output the desired number of words.
from itertools import chain, zip_longest
from random import randint, random, shuffle
s = 'this is a loop'
vowels = []
consonants = []
for char in s.replace(' ', ''):
if char in 'aeiouAEIOU':
vowels.append(char)
else:
consonants.append(char)
shuffle(vowels)
shuffle(consonants)
if len(vowels) > len(consonants) or random() > 0.5:
a, b = vowels, consonants
else:
a, b = consonants, vowels
letters = ''.join([c for c in chain.from_iterable(zip_longest(a, b)) if c])
words = []
for i in range(s.count(' '), -1, -1):
x = randint(1, len(letters) - i)
words.append(letters[:x])
letters = letters[x:]
s = ' '.join(words)
print(s)
# EXAMPLE RANDOM OUTPUT:
# si hipa lo tos
you can do it like this also
separate vowels and consonant using regex
combine each vowels to consonant
shuffle the result until result not starts/ends with space and don't have two spaces together
import random
import re
def perm_lets(st):
ls = re.findall(r"([aeiouAEIOU])|(.)", st)
vs, cs = [c for c,_ in ls if len(c)>0], [v for _,v in ls if len(v)>0]
positions = list(range(len(cs)))
result = ""
for v in vs:
if len(positions)==0:
cs.append(" "+v)
else:
p = random.choice(positions)
positions.remove(p)
cs[p//2] += v
while True:
random.shuffle(cs)
result = "".join(cs)
if not (result.startswith(" ") or result.endswith(" ") or " " in result):
break
return result
print(perm_lets("this is a loop"))
print(perm_lets("teis iou")) # more vowels than consonants
Output
tp so hal osii
si u tei o

Is there an easy way to get longest word that contains a certain letter?

I am trying to get the largest word that contains the letter 'f' through a for loop, through my code I tried to make it as simple as possible with a if and and statement. It is however not working as it returns the largest word but not the one that includes the letter f, why is it not working?
def main():
sentence = "Absence makes the heart grow fonder"
letter = "f"
longest_word = get_longest_word(sentence, letter)
print('"' + longest_word + '" is the longest word containing the letter "'
+ letter + '".')
def get_longest_word(sentence, letter):
words_list = sentence.split()
largest = words_list[0]
my_list = []
for word in words_list:
if letter in word and len(word) > len(largest):
largest = word
return largest
main()
The reason is that you initialise largest to words_list[0], which is 'Absence', the longest word in the sentence.
Therefore, even when 'fonder' is reached, even though the first part of your if passes (it contains an 'f'), the second part about length does not.
Personally, I would just do this:
from operator import itemgetter
def get_longest_word(sentence, letter):
words_with_letter = ((word, len(word)) for word in sentence.split() if letter in word)
return max(words_with_letter, key=itemgetter(1))[0]
This converts the sentence into an iterable of tuples where the first element is the word and the second its length, and where all the words already contain the letter in question.
Then, all we need to do is get the word with the longest length i.e. the highest value in the second position.
Output:
"fonder" is the longest word containing the letter "f".
You can approach this much more easily using the in operator:
for word in word_list:
if 'f' in word:
longest_words.append(word)
longest_word = sorted(longest_words)[0]

Shuffle words' characters while maintaining sentence structure and punctuations

So, I want to be able to scramble words in a sentence, but:
Word order in the sentence(s) is left the same.
If the word started with a capital letter, the jumbled word must also start with a capital letter
(i.e., the first letter gets capitalised).
Punctuation marks . , ; ! and ? need to be preserved.
For instance, for the sentence "Tom and I watched Star Wars in the cinema, it was
fun!" a jumbled version would be "Mto nad I wachtde Tars Rswa ni het amecin, ti wsa
fnu!".
from random import shuffle
def shuffle_word(word):
word = list(word)
if word.title():
???? #then keep first capital letter in same position in word?
elif char == '!' or '.' or ',' or '?':
???? #then keep their position?
else:
shuffle(word)
return''.join(word)
L = input('try enter a sentence:').split()
print([shuffle_word(word) for word in L])
I am ok for understanding how to jumble each word in the sentence but... struggling with the if statement to apply specifics? please help!
Here is my code. Little different from your logic. Feel free to optimize the code.
import random
def shuffle_word(words):
words_new = words.split(" ")
out=''
for word in words_new:
l = list(word)
if word.istitle():
result = ''.join(random.sample(word, len(word)))
out = out + ' ' + result.title()
elif any(i in word for i in ('!','.',',')):
result = ''.join(random.sample(word[:-1], len(word)-1))
out = out + ' ' + result+word[-1]
else:
result = ''.join(random.sample(word, len(word)))
out = out +' ' + result
return (out[1:])
L = "Tom and I watched Star Wars in the cinema, it was fun!"
print(shuffle_word(L))
Output of above code execution:
Mto nda I whaecdt Atsr Swra in hte ienamc, ti wsa nfu!
Hope it helps. Cheers!
Glad to see you've figured out most of the logic.
To maintain the capitalization of the first letter, you can check it beforehand and capitalize the "new" first letter later.
first_letter_is_cap = word[0].isupper()
shuffle(word)
if first_letter_is_cap:
# Re-capitalize first letter
word[0] = word[0].upper()
To maintain the position of a trailing punctuation, strip it first and add it back afterwards:
last_char = word[-1]
if last_char in ".,;!?":
# Strip the punctuation
word = word[:-1]
shuffle(word)
if last_char in ".,;!?":
# Add it back
word.append(last_char)
Since this is a string processing algorithm I would consider using regular expressions. Regex gives you more flexibility, cleaner code and you can get rid of the conditions for edge cases. For example this code handles apostrophes, numbers, quote marks and special phrases like date and time, without any additional code and you can control these just by changing the pattern of regular expression.
from random import shuffle
import re
# Characters considered part of words
pattern = r"[A-Za-z']+"
# shuffle and lowercase word characters
def shuffle_word(word):
w = list(word)
shuffle(w)
return ''.join(w).lower()
# fucntion to shuffle word used in replace
def replace_func(match):
return shuffle_word(match.group())
def shuffle_str(str):
# replace words with their shuffled version
shuffled_str = re.sub(pattern, replace_func, str)
# find original uppercase letters
uppercase_letters = re.finditer(r"[A-Z]", str)
# make new characters in uppercase positions uppercase
char_list = list(shuffled_str)
for match in uppercase_letters:
uppercase_index = match.start()
char_list[uppercase_index] = char_list[uppercase_index].upper()
return ''.join(char_list)
print(shuffle_str('''Tom and I watched "Star Wars" in the cinema's new 3D theater yesterday at 8:00pm, it was fun!'''))
This works with any sentence, even if was "special" characters in a row, preserving all the punctuaction marks:
from random import sample
def shuffle_word(sentence):
new_sentence=""
word=""
for i,char in enumerate(sentence+' '):
if char.isalpha():
word+=char
else:
if word:
if len(word)==1:
new_sentence+=word
else:
new_word=''.join(sample(word,len(word)))
if word==word.title():
new_sentence+=new_word.title()
else:
new_sentence+=new_word
word=""
new_sentence+=char
return new_sentence
text="Tom and I watched Star Wars in the cinema, it was... fun!"
print(shuffle_word(text))
Output:
Mto nda I hctawed Rast Aswr in the animec, ti asw... fnu!

Regex in python search

I'm trying to make something in python where you put the amount of letters in a word then it searches in a word list for words with that amount of chars.
My code:
import sys
import re
def search(pattern):
print("Searching...\n\n")
for i, line in enumerate(open(sys.argv[1])):
for match in re.finditer(pattern, line):
print(match.groups())
print("\n\nFinished.")
while True:
word = ""
put = int(input("Amount of Letters in Word: "))
if put > 25 or put < 3:
print("Invalid amount of letters.")
else:
for n in range(0, put):
word = word + "."
word = "^" + word + "$"
pattern = re.compile(word)
search(pattern)
I want it to show all words with the amount of letters that you put.
https://i.imgur.com/Kgusvyh.png
List of words:
word
1234
okay
0000
asdfg
asdfh
asdgj
Why does it show ()?
Fixed by replacing match.groups() with match.group().

How to scramble the words in a sentence - Python

I have created the following code to scramble the letters in a word (except for the first and last letters), but how would one scramble the letters of the words in a sentence; given the input asks for a sentence instead of a word. Thank you for your time!
import random
def main():
word = input("Please enter a word: ")
print(scramble(word))
def scramble(word):
char1 = random.randint(1, len(word)-2)
char2 = random.randint(1, len(word)-2)
while char1 == char2:
char2 = random.randint(1, len(word)-2)
newWord = ""
for i in range(len(word)):
if i == char1:
newWord = newWord + word[char2]
elif i == char2:
newWord = newWord + word[char1]
else:
newWord = newWord + word[i]
return newWord
main()
May I suggest random.shuffle()?
def scramble(word):
foo = list(word)
random.shuffle(foo)
return ''.join(foo)
To scramble the order of words:
words = input.split()
random.shuffle(words)
new_sentence = ' '.join(words)
To scramble each word in a sentence, preserving the order:
new_sentence = ' '.join(scramble(word) for word in input.split())
If it's important to preserve the first and last letters as-is:
def scramble(word):
foo = list(word[1:-1])
random.shuffle(foo)
return word[0] + ''.join(foo) + word[-1]
Split the sentence into a list of words (and some punctuation) with the split method:
words = input().split()
and then do pretty much the same thing you were doing before, except with a list instead of a string.
word1 = random.randint(1, len(words)-2)
...
newWords = []
...
newWords.append(whatever)
There are more efficient ways to do the swap than what you're doing, though:
def swap_random_middle_words(sentence):
newsentence = list(sentence)
i, j = random.sample(xrange(1, len(sentence) - 1), 2)
newsentence[i], newsentence[j] = newsentence[j], newsentence[i]
return newsentence
If what you actually want to do is apply your one-word scramble to each word of a sentence, you can do that with a loop or list comprehension:
sentence = input().split()
scrambled_sentence = [scramble(word) for word in sentence]
If you want to completely randomize the order of the middle letters (or words), rather than just swapping two random letters (or words), the random.shuffle function is likely to be useful.

Categories