类变量通过for循环保持为空

时间:2018-06-22 05:12:06

标签: python list class for-loop class-variables

我想确保hotel_name列表中不存在Hotel.hotels。 看来,当我每次开始循环进纸时,请查看一个空列表。

请注意,如果我不使用for循环而只能这样做

Hotel.hotels.append([number,hotel_name,city,total_number,empty_rooms])

它打印酒店列表

[[1, 'Crown Plaza', 'alex', 20, 2], [1, 'Crown Plaza', 'alex', 20, 2], [2, 'Radisson Blu', 'cairo', 24, 22], [3, 'Paradise Inn', 'dubai', 390, 200], [4, 'Four Seasons', 'alex', 1000, 400], [5, 'Address', 'dubai', 500, 200], [6, 'Fairmont', 'dubai', 1000, 100], [7, 'Rotana', 'dubai', 5000, 300]]
[Finished in 0.1s]

这是文件

class Hotel():
    """""""""
    this is hotel class file
    """
    hotels = []

    def __init__(self,number,hotel_name,city,total_number,empty_rooms):
        self.number = number
        self.hotel_name = hotel_name
        self.city = city
        self.total_number = total_number
        self.empty_rooms = empty_rooms
        for i in Hotel.hotels:
            if self.hotel_name not in i:
                Hotel.hotels.append([number,hotel_name,city,total_number,empty_rooms])
            # else:
            #     print "Hotel already exists!"

feed_dataBase_with_hotel = Hotel(1,"Crown Plaza","alex",20,2)
feed_dataBase_with_hotel = Hotel(1,"Crown Plaza","alex",20,2)# cull repeated
feed_dataBase_with_hotel = Hotel(2,"Radisson Blu","cairo",24,22)
feed_dataBase_with_hotel = Hotel(3,"Paradise Inn","dubai",390,200)
feed_dataBase_with_hotel = Hotel(4,"Four Seasons","alex",1000,400)
feed_dataBase_with_hotel = Hotel(5,"Address","dubai",500,200)
feed_dataBase_with_hotel = Hotel(6,"Fairmont","dubai",1000,100)
feed_dataBase_with_hotel = Hotel(7,"Rotana","dubai",5000,300)

print Hotel.hotels

非常感谢Patrick的回答 更新 如果我想从字典中建立列表,因为我想访问空房间并使用另一个类更改其值

class Hotel():
    """
    this is hotel class file
    """
    hotels = {}
    hotelList = []

    def __init__(self,number,hotel_name,city,total_number,empty_rooms):
        self.number = number
        self.hotel_name = hotel_name
        self.city = city
        self.total_number = total_number
        self.empty_rooms = empty_rooms

        # edited: no for needed
        if self.hotel_name in Hotel.hotels:
            print('Hotel {} Already exists!'.format(self.hotel_name))
            return # or raise ValueError & handle it

        Hotel.hotels[self.hotel_name] = self

        tempList = Hotel.hotels.items()
        for i in tempList:
            x = Hotel.hotels.items()[i][1]
            Hotel.hotelList.append(x)

更新

另一个预订类将使用我们在酒店类中使用的实例变量hotel_name

from hotel import Hotel
from customer import Customer
from notification import Notification

class Reservation():
    reservations =[]
    def reserve_room(self,hotel_name, customer_name):
        x = Hotel.hotels.values()
        for i in x:
            if Hotel.hotel_name in i:
                Reservation.reservations.append([hotel_name,customer_name])
                i[4] -=1

AttributeError:类Hotel没有属性'hotel_name'

更新 来自Understanding getitem method 使用

def __getitem__(self, hotel_name):
          return self.hotel_name

问题已解决!

特别感谢Patrick

3 个答案:

答案 0 :(得分:1)

我建议更改一些内容以进行修正:

  • 您正在迭代一个可能的1000 Hotel的列表,以查找是否具有相同的名称,如果用set或{{1} },因为其中的查询是dictO(1)个具有List查找最坏情况的时间,这意味着O(n)是恒定时间,而不管您有多少set/dict个。列表变得越来越慢,您需要搜索的Hotel越多。

  • 您用新的酒店实例覆盖了相同的变量,它们自己被创建并被忘记了-您仅将其值存储在Hotel列表中,而不是存储构造的Hotel.hotels本身。 Hotel实例的整个构造是毫无意义的。

建议的更改:

  • 使静态存储成为字典,这使您可以快速查找
  • 存储您的Hotel实例,而不是您用来创建Hotel的值
  • 不要直接打印Hotel-我介绍了一种方法,该方法仅采用您的字典值并按排序方式打印它们-默认情况下,我按Hotel.hotelDict进行排序

Hotel.number

测试:

class Hotel():
    """""""""
    this is hotel class file
    """   
    hotelDict = {} # checking "in" for sets is much faster then list - a dict is similar
                   # fast in checking and can hold values - serves double duty here
    # sorted hotels by value, sorted by key

    @classmethod
    def getSortedHotels(cls, sortKey = lambda x:x.number):
        """Takes all values (Hotel's) from Hotel.hotelDict
        and prints them after sorting. Default sort key is Hotel.number"""
        return sorted(cls.hotelDict.values(), key=sortKey) 

    def __init__(self,number,hotel_name,city,total_number,empty_rooms):
        if hotel_name in Hotel.hotelDict:
            print("Hotel already exists: {}".format(hotel_name))
            return # or raise ValueError("Hotel already exists") and handle the error
# see https://stackoverflow.com/questions/3209233/how-to-replace-an-instance-in-init
# if you want to try to replace it using __new__() but not sure if its possible

        self.number = number
        self.hotel_name = hotel_name
        self.city = city
        self.total_number = total_number
        self.empty_rooms = empty_rooms
        Hotel.hotelDict[self.hotel_name] = self

    def __repr__(self):
        """Neater print output when printing them inside a list"""
        return "{:>3}) {} in {} has {} of wich {} are empty.".format(
        self.number,self.hotel_name,self.city,self.total_number,self.empty_rooms)
        # if you want a "simple" list-like output of your attributes:
        # comment the return above and uncomment:
        # return repr([self.number,self.hotel_name,self.city,
        #              self.total_number,self.empty_rooms])

    def __str__(self):
        """Neater print output when printing Hotel instances"""
        return self.__repr__()

输出:

feed_dataBase_with_hotel = Hotel(1,"Crown Plaza","alex",20,2)
feed_dataBase_with_hotel = Hotel(1,"Crown Plaza","alex",20,2) # cull repeated
feed_dataBase_with_hotel = Hotel(2,"Radisson Blu","cairo",24,22)
feed_dataBase_with_hotel = Hotel(3,"Paradise Inn","dubai",390,200)
feed_dataBase_with_hotel = Hotel(4,"Four Seasons","alex",1000,400)
feed_dataBase_with_hotel = Hotel(5,"Address","dubai",500,200)
feed_dataBase_with_hotel = Hotel(6,"Fairmont","dubai",1000,100)
feed_dataBase_with_hotel = Hotel(7,"Rotana","dubai",5000,300)

print Hotel.getSortedHotels() 

print Hotel(99,"NoWayInn","NoWhere",1,200)

如果要按名称对酒店进行排序,请轻松:

Hotel already exists: Crown Plaza
[  1) Crown Plaza in alex has 20 of wich 2 are empty.,   
   2) Radisson Blu in cairo has 24 of wich 22 are empty.,   
   3) Paradise Inn in dubai has 390 of wich 200 are empty.,   
   4) Four Seasons in alex has 1000 of wich 400 are empty.,   
   5) Address in dubai has 500 of wich 200 are empty.,   
   6) Fairmont in dubai has 1000 of wich 100 are empty.,   
   7) Rotana in dubai has 5000 of wich 300 are empty.]

 99) NoWayInn in NoWhere has 1 of wich 200 are empty.

答案 1 :(得分:0)

看看这条线我在Hotel.hotels中的位置:在这里

for i in Hotel.hotels:
    if self.hotel_name not in i:
          Hotel.hotels.append([number,hotel_name,city,total_number,empty_rooms])

并尝试在这种情况下它将填充您的数组

答案 2 :(得分:0)

问题是,您在遍历空的“酒店”列表时追加了。 首先在for循环中检查现有的hotel_name,然后再追加。

for hotel in self.hotels:
    if self.hotel_name == hotel[1]:  # hotel_name is at index 1
        print('Already exists!')
        return  # return before appending
#now append
self.hotels.append([number,hotel_name,city,total_number,empty_rooms])

如果您不想返回,请尝试此

for hotel in self.hotels:
    if self.hotel_name == hotel[1]:  # hotel_name is at index 1
        print('Already exists!')
        break
else:  # break did not happen
    self.hotels.append([number,hotel_name,city,total_number,empty_rooms])