Replacing in Python - python

I need to complete a basic task on Python that requires me to convert a standard phone number into an international one.
So for example, if the users phone number was 0123456789, the program should display, Your international phone number is +44123456789.
I don't know how to replace the 0 with a 44. I don't know many techniques on Python so advice on how to is welcomed, thanks.
EDIT:
#Python Number Conversion
def GetInternational(PhoneNumber):
if num.startswith('0'):
num = num.replace('0','+44',1)
return GetInternational
PhoneNumber = input("Enter your phone number: ")
print('Your international number is',GetInternational,'')
I'm missing something obvious but not sure what...

Another way to do it would be:
num.replace('0','+44',1) #Only one, the leftmost zero is replaced
Therefore if the number starts with zero we replace only that one,
num = "0123456789"
if num.startswith('0'):
num = num.replace('0','+44',1)

Well the simplest way to do it is strip off the first character (the 0) and then concatenate it with +"44":
num = "0123456789"
if num.startswith("0"):
num = "+44" + num[1:]
For clarity I added a startswith check to make sure the substitution only happens if the number starts with a zero.

Related

Python input multiple lines and spaces

Im trying to solve one of the a2oj problems "given three numbers a , b and c. print the total sum of the three numbers added to itself."
I came with this
import sys
numbers = [int(x) for x in sys.stdin.read().split()]
print(numbers[0] + numbers[1] + numbers[2])
I saw many topics but I cant figure out how to read just 3 values from input. I know I can stop this procces by typing CTRL+D, but is there any possibility to make it automatic (after reaching third value)?
Thanks
// Thanks for very quick answers, I made mistake and posted only Problem Statement without Input Format: "three numbers separated by bunch of spaces and/or new lines"
So for example input should look like this:
2
1 4
// Ok thanks to you guys finally I made this:
n = []
while len(n) < 3:
s=input()
i = s.split()
[n.append(int(j)) for j in i]
print(2 * sum(n))
It's working but when I sent my results I got Runtime Error. I have no idea why:
Link: https://a2oj.com/p?ID=346
You could just use:
sys.argv
import sys
numbers = [int(x) for x in sys.argv[1:4]]
print(numbers)
print(sum(numbers))
When inputs are given line by line.
from sys import stdin
sum = 0
for num in stdin.readline(4):
sum = sum + int(num)
print(sum)
When inputs are given on CLI.
from sys import argv
sum = 0
for num in argv[1:4]:
sum = sum + int(num)
print(sum)
Use Python strip() and split() functions as per your usecases
I am not sure what you are looking for, but it seems that you are looking for is the input function, from python's builtins:
x=input()
This reads any input from the user, as a string. You have then to convert it to a number if needed.
You can read three values:
x=input("First value:")
y=input("Second value:")
z=input("Third value:")
As you have now specified more precisely the problem statement, I edit my answer:
In your case, this is not very complicated. I am not going to give you the answer straight away, as it would defeat the point, but the idea is to wrap the input inside a while loop. Something like:
numbers=[]
while (you have less than 3 numbers):
(input one line and add the numbers to your list)
(print the sum of your numbers)
That way you are waiting for as many inputs as you need until you reach 3 numbers. By the way, depending on your input, you might have to check whether you do not get more than 3 numbers.
After seeing the update from the question author and linked the online judge question description, the tweak to his code needed is below. It's worth noting that the expected output is in float and has precision set to 6 and the output is 2 * sum of all inputs, not just sum. There is no description on this in the online judge question and you've to understand from the input vs output.
n = []
while len(n) < 3:
s = input()
i = s.split()
n.extend(float(j) for j in i)
print(format(2 * sum(n), '.6f'))
Screenshot below
But the first version of this answer is still valid to the first version of this question. Keeping them if anyone else is looking for the following scenarios.
To separate inputs by enter aka New lines:
numbers_List = []
for i in range(3):
number = int(input())
numbers_List.append(number)
print("Sum of all numbers: ", sum(numbers_List))
Screenshot:
To separate inputs by space aka Bunch of spaces:
Use map before taking input. I'd suggest using input as well instead of sys.stdin.read() to get input from users, separated by space, and ended by pressing Enter key.
Very easy implementation below for any number of inputs and to add using sum function on a list:
numbers = list(map(int, input("Numbers: ").split()))
print("Sum of all numbers: ", sum(numbers))
The screenshot below and link to the program is here
Read Python's Built-in Functions documentation to know more about all the functions I used above.

Why is this random generator sometimes returning 3 digits instead of 4?

if choice == '1':
print('Your card has been created')
card = create_card()
print(f'Your card number:\n{card}')
pin = int(''.join(f'{random.randint(0, 9)}' for _ in range(4)))
print(f'Your card PIN:\n{pin}\n')
cards.append([card, pin])
Please can someone explain why the above code sometimes generates a 3-digit number as opposed to a 4-digit number? For example:
Others have explained why you sometimes end up with three-digit (or even two- or one-digit) results. You could view this as a formatting problem -- printing a number with leading zeroes to a specified width. Python does have features supporting that.
But I urge you to instead recognize that the problem is really that your data isn't actually a number in the first place. Rather, it is a string of digits, all of which are always significant. The easiest and best thing to do, then, is to simply keep it as a string instead of converting it to a number.
Your random generator is not returning four-digit numbers sometimes since it is putting a zero as the first digit. Numbers like 0322 are created by the random generator and it is being converted to 322. This generator can also make two-digit and one-digit numbers because of the zeros in front. If you want four-digit numbers only use pin = random.randint(1000, 9999). If you want numbers with leading zeros, use pin = ''.join(f'{random.randint(0, 1)}' for _ in range(4)). This keeps the leading zeros. Keeping the pin as a string stops the leading zeros from being removed.
In your logic, it's possible to generate a string that starts with 0. If you pass a leading 0 numeric string to int(), that leading 0 is ignored:
print(int("0999"))
Output
999
To fix this, you could just change the range start value.
pin = int(''.join(f'{random.randint(1, 9)}' for _ in range(4)))
Edit: To prove this to yourself, print both the generated string and the result of the int() function, like below.
for i in range(100):
st = ''.join(f'{random.randint(0, 9)}' for _ in range(4))
print(st, int(st))

How to limit the amount of numbers given in a float input? (Python)

Novice Pythoner here. I am trying to finish my first program (a tip calculator) and I have one last piece of code to write. Here is the part of code I need to add on to:
bill_amt = True
while bill_amt:
try:
bill_amt = float(input('First, what was the price of your meal?:'))
except:
print('Please enter a number only.')
continue
if bill_amt <= 0:
print('Your meal wasn\'t $',bill_amt,'! Please try again.')
bill_amt = True
else:
x = float(bill_amt)
bill_amt = False
What I want to do is add a command that will limit the amount of numbers you can input when the code asks how much your meal was so user can't type in 4511511513545513513518451.32. I've tried using len(bill_amt) > 8, but I get an error that floats don't have strings. How do I get around this? Thanks, sorry if it's a duplicate! -Pottsy
use regex matching, this will also prevent the user from typing in something like "12.123456"
import re
# ...
while True:
inp = input('First, what was the price of your meal?:'))
if bool(re.match(r"^\d{1,8}\.\d\d$", inp)):
return float(inp)
else:
print('invalid entry')
\d means digit, {1,8} means allow anywhere from 1 to 8 digits. \d\d looks for two digits after the ., so this regex will match 1-8 digits, followed by a dot, followed by two more digits.
Note that if you are dealing with money, you don't generally want to use floats, but rather decimal.Decimals. Try doing
decimal.Decimal(inp)
at the end instead.
In order to get the length use str(bill_amount)
len(str(123.53)) is 6
Note that even though Python will allow you to use a float value and then change it to the boolean, it would be better to make it a different name rather than have both the float and the boolean as bill_amt
.
Float doesn't have length but str does:
bill_amt_str = input('First, what was the price of your meal?:')
if len(bill_amt_str.replace(".", "")) > 8:
print("No more than 8 digits please.")
continue
bill_amt = float(bill_amt_str)

converting a random integer to a string

I'm struggling to understand how I would change this code. Instead of converting the input value to an integer before comparing it to the random integer, I want to convert the random integer to a string and then do the comparison (comparing the string to a string). I am a beginner in programming. Also, I don't want the answer I'm asking, just how to understand it better and where I should start. I apologize that this might seem easy to people, but I'm struggling with it.
import random
#this function generates a random number between 1 and 100 and asks the user to guess the number
def playGame2():
number = random.randint(1,100)
guess = input("I'm thinking of a number between 1 and 100. Guess what it is: ")
if number == int(guess):
print("That is correct!")
else:
print("Nope...I was thinking of " + str(number))
As Mark Ransom said above, you've essentially already answered your own question; using str converts to a string, much like int converts to an integer.
To use this most effectively, you can convert your random integer to a string immediately after generation:
number = str(random.randint(1,100))
Now, since number and guess are both strings, there's no need to do any further casting in order to compare or print them.
You're still having to deal with the fact that I can enter eight instead of 8. You're real close and everyone's help has gotten you there but try and use some exception handling here just in case, it's NEVER too early to start handling exceptions!
def playGame2():
number = str(random.randint(1,100))
try:
guess = input("I'm thinking of a number between 1 and 100. Guess what it is: ")
if number == int(guess):
print("That is correct!")
else:
print("Nope...I was thinking of " + str(number))
except:
print "Oops, please use a numeric value."
playGame2()
This will get you through the NameError that you get if someone types out a word. I know this is probably just for you or a class but it's still good practice.
message = input('Message: ')
print(ascii(message)

International phone number validation

I need to do pretty basic phone-number validation and formatting on all US and international phone numbers in Python. Here's what I have so far:
import re
def validate(number):
number = re.compile(r'[^0-9]').sub('', number)
if len(number) == 10:
# ten-digit number, great
return number
elif len(number) == 7:
# 7-digit number, should include area code
raise ValidationError("INCLUDE YOUR AREA CODE OR ELSE.")
else:
# I have no clue what to do here
def format(number):
if len(number) == 10:
# basically return XXX-XXX-XXXX
return re.compile(r'^(\d{3})(\d{3})(\d{4})$').sub('$1-$2-$3', number)
else:
# basically return +XXX-XXX-XXX-XXXX
return re.compile(r'^(\d+)(\d{3})(\d{3})(\d{4})$').sub('+$1-$2-$3-$4', number)
My main problem is that I have NO idea as to how international phone numbers work. I assume that they're simply 10-digit numbers with a \d+ of the country code in front of them. Is this true?
E.164 numbers can be up to fifteen digits, and you should have no expectation that beyond the country code of 1-3 digits that they will fit any particular form. Certainly there are lots of countries where it is not XXX-XXX-XXXX. As I see it you have three options:
Painstakingly create a database of the number formats for every country code. Then check each country individually for updates on a periodic basis. (Edit: it looks like Google already does this, so if you trust them and the Python porter to keep libphonenumber correct and up to date, and don't mind upgrading this library every time there is a change, that might work for you.)
Eliminate all delimiters in the supplied telephone numbers and format them without any spacing: +12128675309
Format the numbers as the user supplies them rather than reformatting them yourself incorrectly.
I ignore the format as in where are the spaces and dashes.
But here is the regex function I use to validate that numbers:
eventually, start with a + and some digits for the country code
eventually, contain one set of brackets with digits inside for area code or optional 0
finish with a digit
contain spaces or dashes in the number itself (not in the country or area codes):
def is_valid_phone(phone):
return re.match(r'(\+[0-9]+\s*)?(\([0-9]+\))?[\s0-9\-]+[0-9]+', phone)

Categories