VediVY
VediVY

Reputation: 23

Python Looping through input().split()

I'm trying to write a code that verifies the if password entered matches the criteria given below.


  1. At least 1 letter between [a-z]
  2. At least 1 number between [0-9]
  3. At least 1 letter between [A-Z]
  4. At least 1 character from [$#@]
  5. Minimum length of transaction password: 6
  6. Maximum length of transaction password: 12

Output and code screenshot

import re
tmp=[]
for i in input().split(','):
  print(i)
  upp=0
  low=0
  dig=0
  sch=0
  for j in i:
    if j.isdigit() and dig!=1:
      dig=1
    elif j.isupper() and upp!=1:
      upp=1
    elif j.islower() and low!=1:
      low=1
    elif re.search("[$#@]",j) and sch!=1:
      sch=1
    elif dig and sch and low and upp and (len(i)>=6 and len(i)<=12)==True:
      tmp+=[i]
      print(i)
      print(tmp)
print(','.join(tmp))

The test case is

This@me1,notThis,Fine@3456,&1234567sdfD

It seems like its looping through one of the test cases thrice?

The output looks like :

This@me1
notThis
Fine@3456
Fine@3456
['Fine@3456']
Fine@3456
['Fine@3456', 'Fine@3456']
Fine@3456
['Fine@3456', 'Fine@3456', 'Fine@3456']
&1234567sdfD
Fine@3456,Fine@3456,Fine@3456

Not entirely sure what is causing this. Why is it running the Fine@3456 case thrice? Also, I fail to understand why the first case This@me1 also does not get recognized as valid.

Any help will be much appreciated!

Note: I'm running this code online-on repl.it: https://IroncladSoulfulKiskadee.yashvedi.repl.run <- To run the test case

Python 3.6.1 (default, Dec 2015, 13:05:11) [GCC 4.8.2] on linux

ps. Please ignore the redundancy in the code;

Thanks.

Upvotes: 2

Views: 374

Answers (2)

norbeq
norbeq

Reputation: 3076

Maybe instead of checking all words characters in a loop do something like this (Its more readable):

import re
tmp=[]
for i in input().split(','):
  if not (6 <= len(i) <= 12):
    continue
  if not re.search("[$#@]", i):
    continue
  if not re.search("[a-z]", i):
    continue
  if not re.search("[A-Z]", i):
    continue
  if not re.search("[0-9]", i):
    continue
  tmp.append(i)
print(','.join(tmp))

Upvotes: 0

user2201041
user2201041

Reputation:

elif dig and sch and low and upp and (len(i)>=6 and len(i)<=12)==True:
  tmp+=[i]

This is not happening in the right place. Consider the password This@me1. At the last iteration of the inner loop, will we execute

if j.isdigit() and dig!=1:
  dig=1

And then none of the elif stuff goes through (including your final check).

The issue with Fine@3456 running three times is due to a very similar problem.

To fix:

for j in i:
    if j.isdigit() and dig!=1:
      dig=1
    elif j.isupper() and upp!=1:
      upp=1
    elif j.islower() and low!=1:
      low=1
    elif re.search("[$#@]",j) and sch!=1:
      sch=1
if dig and sch and low and upp and (len(i)>=6 and len(i)<=12)==True:
  tmp+=[i]

Check if the condition holds after you've checked everything.

(And consider using True and False instead of 1 and 0. That's why they're there.)

Upvotes: 1

Related Questions