尝试使用类从列表中删除项目

时间:2019-06-29 07:33:56

标签: python-3.x oop

我正在尝试为我正在使用面向对象编程的该地址簿程序实现一个remove entry选项。我遇到的问题是,当我尝试从列表中删除一个元素时,它会删除除最后一个元素以外的所有元素。

我尝试在AddressBook类的remove_entry函数中创建列表并对其进行迭代,而不是尝试直接从我在Address Book类的init函数中初始化的self.people列表中删除该元素。这类似于我在控制器类中执行的display_summaries函数,但是并不能解决我的问题。当我尝试执行此操作时,它没有从列表中删除任何元素。

# Imports
import pickle
import os.path

# Constants
SAVE_FILE_NAME = 'address_book_contents.pickle'
INSTRUCTIONS = '''Address Book Application
Press:
a to add an entry
r to remove an entry
d to display a list of all entries in summary form
s to display a list of all entries sorted alphabetically in summary form
i to print these instructions again
q to quit
'''
CONFIRM_QUIT_MESSAGE = 'Are you sure you want to quit (Y/n)? '
SUMMARY_TEMPLATE = "%s %s DOB: %s email: %s"

### Classes Section
class AddressBook (object):
    ''' 
    This class holds and manages a list of my contacts 
    '''

    def __init__ (self):
        ''' Set people attribute to an empty list '''
        self.people = []

    def add_entry (self, new_entry):
        ''' Adds a new entry to the list of people in the address
        book. The new_entry is an instance of the AddressEntry
        class'''
        #Adds the entry to people list
        self.people.append(new_entry)

    def remove_entry(self, entry):
        '''Removes an entry from the list of people in the address book.
        Entry is an index and comes from the remove_entry function in
        the Controller class '''
        try:
            entry = int(entry)
            #return self.people.remove(self.people[entry-1])

        except IndexError:
            #print("INVALID ENTRY! There is no entry in the address book for the number you entered")
            return "INVALID ENTRY! There is no entry in the address book for the number you entered"
        except ValueError:
            return "INVALID ENTRY! Please enter an integer number instead of a character"
        else:
            entry = int(entry)
            del self.people[entry-1]

    def is_list_empty (self):
        return self.people

    def save(self):
        with open(SAVE_FILE_NAME, 'wb') as file_object:
            pickle.dump(self, file_object)



class AddressEntry (object):
    '''
    This class has one instance for each person's details
    '''
    def __init__ (self, first_name=None, last_name=None, email=None, DOB=None):
        '''Initializes attributs f_name, l_name, email, and birthday.
        Each arg is a string.
        Birthday should be a string in the format MM DD, YYYY
        '''
        self.first_name = first_name
        self.last_name = last_name
        self.email = email
        self.DOB = DOB

    #Function that overites default __repr__ so that print(person1) actually prints the values we passed into __init__
    def __repr__ (self):
        '''Given an AddressEntry object self return a readable string
        representation
        '''
        template = "AddressEntry(first_name = '%s', "+\
                "last_name = '%s', "+\
                "email = '%s', "+\
                "DOB = '%s')"

        attributes = (self.first_name, self.last_name, self.email, self.DOB)

        return template%attributes



class Controller(object):

    def __init__(self):
        self.address_book = self.load()
        if self.address_book is None:
            self.address_book = AddressBook()

        self.run_interface()

    def load(self):
        if os.path.exists(SAVE_FILE_NAME) is True:
            with open(SAVE_FILE_NAME, 'rb') as file_object:
                address_book = pickle.load(file_object)
            return address_book
        else:
            return None

    def run_interface(self):

        print(INSTRUCTIONS)
        while True:
            command = input('What would you like to do? (press i to see all the options again) ')
            type(command)
            if command == 'a':
                self.add_entry()
            elif command == 'r':
                self.remove_entry()
            elif command == 'd':
                print("Displaying summaries of all people stored in the address book")
                self.display_summaries()
            elif command == 's':
                self.sort_entries()
            elif command == 'i':
                print(INSTRUCTIONS)
            elif command == 'q':
                user_quit = input(CONFIRM_QUIT_MESSAGE)
                type(user_quit)
                if user_quit == 'Y' or user_quit == 'y':
                    print('\nSaving...')
                    self.address_book.save()
                    print("\nThank you for using my address book application; come again soon!")
                    break
                elif user_quit == 'N' or user_quit == 'n':
                    continue
            else:
                print("I don't recognize that instruction (%s) "%command)

    def add_entry(self):
        print("Adding a new person to the address book")
        print("What is the person's: ")
        first_name = input("First Name? ")
        type(first_name)
        if first_name == 'q':
            print('Not Adding')
            return
        last_name = input("Last Name? ")
        type(last_name)
        if last_name == 'q':
            print('Not Adding')
            return
        email = input("Email Address? (if they don't have one, just enter None) ")
        type(email)
        if email == 'q':
            print('Not Adding')
            return
        DOB = input("Date of Birth? (Enter in the format MM DD, YYYY) ")
        type(DOB)
        if DOB == 'q':
            print('Not Adding')
            return

        new_entry = AddressEntry(first_name, last_name, email, DOB)
        self.address_book.add_entry(new_entry)
        values = (first_name, last_name)
        print("Added address entry for %s %s\n"%values)

    def display_summaries(self):
        '''for index, e in enumerate(self.address_book.people):
            values = (e.first_name, e.last_name, e.DOB, e.email)
            entry = SUMMARY_TEMPLATE%values
            print("%s: %s"%(index+1, entry))'''
        if self.address_book.is_list_empty() == []:
            print("Cannot display summaries because the address book is empty")
            return
        else:
            list1 = []
            for i in self.address_book.people:
                values = (i.first_name, i.last_name, i.DOB, i.email)
                list1.append(values)

            list1 = sorted(list1)

            for index, e in enumerate(list1):
                entry = SUMMARY_TEMPLATE%e
                print("%s: %s"%(index+1, entry))

    def remove_entry(self):
        print("Removing a person from the address book\n")
        if self.address_book.is_list_empty() == []:
            print("There are no entries to remove from the address book")
            return
        else:
            self.display_summaries()
            while True:
                user_input = input("\nEnter the number of the entry you would like to remove: ")
                type(user_input)
                if user_input == 'q':
                    print("Exiting remove entry")
                    return

                if self.address_book.remove_entry(user_input) == "INVALID ENTRY! There is no entry in the address book for the number you entered":
                    print(self.address_book.remove_entry(user_input))
                elif self.address_book.remove_entry(user_input) == "INVALID ENTRY! Please enter an integer number instead of a character":
                    print(self.address_book.remove_entry(user_input))
                else:
                    print("Entry number "+user_input+" has been removed")
                    break

    def sort_entries(self):
        print("Sorting Entries")
        if self.address_book.is_list_empty() == []:
            print("Cannot sort because the address book is empty")
            return
        else:
            list1 = []
            for i in self.address_book.people:
                values = (i.first_name, i.last_name, i.DOB, i.email)
                list1.append(values)

            list1 = sorted(list1)

            for index, e in enumerate(list1):
                entry = SUMMARY_TEMPLATE%e
                print("%s: %s"%(index+1, entry))



### Main section
controller = Controller()

这是我尝试仅从列表中删除第一个元素时得到的输出:

What would you like to do? (press i to see all the options again) r
Removing a person from the address book

1: Eric s DOB: 1 email: 1
2: Joe J DOB: 1 email: N
3: Joe S DOB:  email: 


Enter the number of the entry you would like to remove: 1
Entry number 1 has been removed

What would you like to do? (press i to see all the options again) d
Displaying summaries of all people stored in the address book
1: Joe S DOB:  email: 

我期望得到的是:

Enter the number of the entry you would like to remove: 1
Entry number 1 has been removed

What would you like to do? (press i to see all the options again) d
Displaying summaries of all people stored in the address book
1: Joe J DOB: 1 email: N
2: Joe S DOB:  email: 

1 个答案:

答案 0 :(得分:0)

您的主要问题在于这个小块:

if self.address_book.remove_entry(user_input) == "INVALID ENTRY! There is no entry in the address book for the number you entered":
    print(self.address_book.remove_entry(user_input))
elif self.address_book.remove_entry(user_input) == "INVALID ENTRY! Please enter an integer number instead of a character":
    print(self.address_book.remove_entry(user_input))
else:
    print("Entry number "+user_input+" has been removed")
    break

在类remove_entry的{​​{1}}方法中。

请注意,在Controllerif中,您每次都使用表达式elif 实际上调用。因此,发生的事情是在self.address_book.remove_entry(user_input)的第一次检查中删除了第一个条目,然后在if的检查中删除了第二个条目!

您要执行的操作是一次调用删除功能,然后执行检查。像这样:

elif

除了您的代码有几个问题或键入的代码不正确。如果您是初学者,建议您从更简单的项目开始,以掌握它。