Adding string after each vowel

Question:

I am currently on a project to develop a small, fun program that takes a name as an input and returns the name with the string "bi" after each vowel in the name.

I am encountering the problem that my program runs in an infinite loop when I have a name that has same the same vowel twice, for example: the name "aya". technically it should return "abiyabi"

"""Welcome to the code of BoBi Sprache. This Sprache aka Language will 
put the letter "bi" after each vowel letter in your name"""

print("Welcome to the BoBiSprache programm")
Name = input("Please enter your name to be BoBied :D : ")
NameList = list(Name.lower())

vowels = ["a", "e", "i", "o", "u"]


def VowelCheck(NameList):
    for i in NameList:
        index = NameList.index(i)
        for j in vowels:
            if i == j and index == 0:
                NameList.insert(index + 1, "bi")

            elif i == j and (str(NameList[index - 1]) + str(NameList[index])) != "bi":
                NameList.insert(index + 1, "bi")


VowelCheck(NameList)
NewName = ""
NewName = (NewName.join(NameList)).title()
print("Your New Name is: %s" % NewName)

I thought first it is a problem with the first letter being a vowel. but I added an if statement that should solve that. I’m honestly out of answers now, and seeking help. You guys might see something I don’t see.

Asked By: Mohammed Sabaawi

||

Answers:

The reason your function keeps on looping is as you said that you have the same vowel twice while you also search for the index of the vowel. The problem with that is the index method returns the first instance of the value being searched. When you iterate to the next element of your list it remains the same value as before being that you’re editing your list while iterating through it. It also won’t be "bi" because that was added after the first instance of the vowel.

It’s not recommended to edit a list during iteration. Best practice would be to create a new list and append values to it.

Answered By: CodeKorn

Build the Bobied name independent of the user-submitted name. Also note that strings are iterables in Python and there’s no need to convert the user-submitted name to a list.


username = input("Please enter your name to be BoBied :D : ")
vowels = ["a", "e", "i", "o", "u"]


def VowelCheck(name):
    bobified_name = ""
    for i in name:
        bobified_name += i
        if i in vowels:
            bobified_name += "bi"
    return bobified_name


print("Your New Name is: %s" % VowelCheck(username).title())

Now, if you want to avoid the loops and conditionals, or have large input: use str.translate(). First make a translation table, just a dict which maps vowels to bobified vowels. Then call translate() on the name to be bobified.

username = input("Please enter your name to be Bobied :D : ")
bobi_table = str.maketrans({
    'a': 'abi',
    'e': 'ebi',
    'i': 'ibi',
    'o': 'obi',
    'u': 'ubi'
})
print("Your new name is: %s" % username.translate(bobi_table))
Answered By: Michael Ruth

You can also do this by using str.translate which you can give multiple-characters to change one character into many:

username = input("Please enter your name to be BoBied :D : ")
vowels = ["a", "e", "i", "o", "u"]
vowels += [i.upper() for i in vowels]
translation_table = str.maketrans({i: i+"bi" for i in vowels})

print((f"Your BoBied name is: {username.translate(translation_table)}"))

Demo:

Please enter your name to be BoBied :D : Hampus
Your BoBied name is: Habimpubis

I also added upper-case letters, so that it doesn’t matter in what case that the user inputs their name.

Answered By: Hampus Larsson