"""
Exercise 2: cooperative super() chain across multiple inheritance

Implement three classes forming a diamond, where EVERY describe()
method calls super().describe() and appends its own tag, so that
calling describe() on a Combined instance returns a string
concatenating every class's contribution exactly once, in MRO order.

  class Base:       describe() -> "Base"
  class Left(Base):  describe() -> super() result + "+Left"
  class Right(Base):  describe() -> super() result + "+Right"
  class Combined(Left, Right): describe() -> super() result + "+Combined"
    (Combined does NOT need to override describe if Left/Right/Base
     chain correctly — but you may add one if it's cleaner; if you do,
     it must still call super().describe() first.)

Expected MRO-driven result for Combined().describe():
  "Base+Right+Left+Combined"
(because Combined.__mro__ is (Combined, Left, Right, Base, object),
and each class's super().describe() call happens BEFORE appending its
own tag, so the string builds from Base outward.)
"""

class Base:
    def describe(self):
        # TODO: return "Base"
        pass


class Left(Base):
    def describe(self):
        # TODO: return super().describe() + "+Left"
        pass


class Right(Base):
    def describe(self):
        # TODO: return super().describe() + "+Right"
        pass


class Combined(Left, Right):
    def describe(self):
        # TODO: return super().describe() + "+Combined"
        pass


# --- self-check: do not modify below this line ---
result = Combined().describe()
mro_names = [c.__name__ for c in Combined.__mro__]

checks = [
    (result, "Base+Right+Left+Combined"),
    (mro_names, ["Combined", "Left", "Right", "Base", "object"]),
]

all_passed = all(actual == expected for actual, expected in checks)
for actual, expected in checks:
    print(f"got {actual!r}, expected {expected!r} -> {'PASS' if actual == expected else 'FAIL'}")

print("ALL PASS" if all_passed else "SOME FAILED")
