You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何基于现有类创建可按层类型与下标访问的蛋糕类?

实现支持下标与类名访问的蛋糕分层对象

需要将多个预定义类(如Frosting、Bread、Filling)的实例组合成一个新对象,要求同时支持两种访问方式:

  1. 通过下标访问各层实例
  2. 通过层的类名直接访问对应实例

现有预定义类代码:

class Frosting(object):
  def __init__(self, Size, flavor):
    self.Size = Size
    self.flavor = flavor

class Bread(object):
  def __init__(self, Size, flavor):
    self.Size = Size
    self.flavor = flavor

class Filling(object):
  def __init__(self, Size, flavor):
    self.Size = Size
    self.flavor = flavor

当前仅能通过列表下标访问:

layer0 = Bread(10, 'Vanilla')
layer1 = Frosting(5, 'Chocolate') 

newCake = [layer0, layer1]
# 仅能通过下标访问:newCake[1].flavor

期望实现BuildCake类,达成如下使用效果:

CakeFoo = BuildCake(newCake)
print(CakeFoo.Frosting.flavor)  # 输出Chocolate
print(CakeFoo[0].flavor)        # 输出Vanilla

解决方案

实现BuildCake类时,需要完成两个核心逻辑:

  • 存储所有层实例,支持下标访问(通过实现__getitem__魔法方法)
  • 将每个层实例按类名绑定为对象属性(通过setattr动态设置)

基础实现(单类单实例场景)

class BuildCake(object):
    def __init__(self, layers):
        # 存储所有层的列表,用于下标访问
        self.layers = layers
        # 遍历每个层,将类名作为属性绑定到当前对象
        for layer in layers:
            layer_class_name = type(layer).__name__
            setattr(self, layer_class_name, layer)
    
    # 实现下标访问的魔法方法
    def __getitem__(self, index):
        return self.layers[index]

测试验证

layer0 = Bread(10, 'Vanilla')
layer1 = Frosting(5, 'Chocolate') 
CakeFoo = BuildCake([layer0, layer1])

# 通过类名访问
print(CakeFoo.Frosting.flavor)  # 输出: Chocolate
# 通过下标访问
print(CakeFoo[0].flavor)        # 输出: Vanilla

扩展:支持同类型多实例场景

如果蛋糕存在多个同类型层(比如两层Frosting),基础实现会导致后面的实例覆盖前面的。可以修改逻辑,将同类型实例存储为列表:

class BuildCake(object):
    def __init__(self, layers):
        self.layers = layers
        # 初始化一个字典存储类名到实例列表的映射
        self.layer_map = {}
        for layer in layers:
            layer_class_name = type(layer).__name__
            if layer_class_name not in self.layer_map:
                self.layer_map[layer_class_name] = []
            self.layer_map[layer_class_name].append(layer)
            # 绑定属性:如果只有一个实例则直接赋值,否则赋值为列表
            if len(self.layer_map[layer_class_name]) == 1:
                setattr(self, layer_class_name, layer)
            else:
                setattr(self, layer_class_name, self.layer_map[layer_class_name])
    
    def __getitem__(self, index):
        return self.layers[index]

多实例场景测试

layer0 = Bread(10, 'Vanilla')
layer1 = Frosting(5, 'Chocolate')
layer2 = Frosting(3, 'Strawberry')
CakeFoo = BuildCake([layer0, layer1, layer2])

print(CakeFoo.Frosting[0].flavor)  # 输出: Chocolate
print(CakeFoo.Frosting[1].flavor)  # 输出: Strawberry
print(CakeFoo[2].flavor)           # 输出: Strawberry

内容的提问来源于stack exchange,提问作者Robert Simpson

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.25 15:15:10