""" https://stepik.org/lesson/701994/step/10?unit=702095 В программе необходимо реализовать таблицу TableValues по следующей схеме: Каждая ячейка таблицы должна быть представлена классом Cell. Объекты этого класса создаются командой: cell = Cell(data) где data - данные в ячейке. В каждом объекте класса Cell должен формироваться локальный приватный атрибут __data с соответствующим значением. Для работы с ним в классе Cell должно быть объект-свойство (property): data - для записи и считывания информации из атрибута __data. Сам класс TableValues представляет таблицу в целом, объекты которого создаются командой: table = TableValues(rows, cols, type_data) где rows, cols - число строк и столбцов таблицы; type_data - тип данных ячейки (int - по умолчанию, float, list, str и т.п.). Начальные значения в ячейках таблицы равны 0 (целое число). С объектами класса TableValues должны выполняться следующие команды: table[row, col] = value# запись нового значения в ячейку с индексами row, col (индексы отсчитываются с нуля) value = table[row, col] # считывание значения из ячейки с индексами row, col for row in table: # перебор по строкам for value in row: # перебор по столбцам print(value, end=' ') # вывод значений ячеек в консоль print() При попытке записать по индексам table[row, col] данные другого типа (не совпадающего с атрибутом type_data объекта класса TableValues), должно генерироваться исключение командой: raise TypeError('неверный тип присваиваемых данных') При работе с индексами row, col, необходимо проверять их корректность. Если индексы не целое число или они выходят за диапазон размера таблицы, то генерировать исключение командой: raise IndexError('неверный индекс') P.S. В программе нужно объявить только классы. Выводить на экран ничего не нужно. """ class Cell: def __init__(self, data=0): self.__data = data @property def data(self): return self.__data @data.setter def data(self, value): self.__data = value def __eq__(self, other): if hasattr(other, "data"): return self.data == other.data return self.data == other def __ne__(self, other): return not self == other @classmethod def wrap(cls, value): return value if isinstance(value, cls) else cls(value) def __repr__(self): return f"{self.__class__.__name__}({self.data!r})" def __str__(self): return str(self.data) class TableValues: def __init__(self, rows, cols, type_data=int, data=None): self.rows, self.cols, self.type_data = rows, cols, type_data if data: self.cells = tuple(tuple(Cell.wrap(x) for x in row) for row in data) else: self.cells = tuple( tuple(Cell.wrap(self.type_data()) for _ in range(cols)) for _ in range(rows) ) def __len__(self): return self.rows def validate_index(self, index): if not isinstance(index, tuple): raise IndexError("неверный индекс") row, col = index if ( not isinstance(row, int) or not 0 <= row < self.rows or not isinstance(col, int) or not 0 <= col < self.cols ): raise IndexError("неверный индекс") return row, col def __getitem__(self, index): row, col = self.validate_index(index) return self.cells[row][col].data def __setitem__(self, index, new_value): row, col = self.validate_index(index) if not isinstance(new_value, self.type_data): raise TypeError("неверный тип присваиваемых данных") self.cells[row][col].data = new_value def __iter__(self): return ( (self.cells[row][col].data for col in range(self.cols)) for row in range(self.rows) ) def __repr__(self): return f"{self.__class__.__name__}({self.rows!r}, {self.cols!r}, {self.type_data.__name__}, {self.cells!r})" def tests(): code = ( b"bYdVqAXH&uY-LtqY;|RGC^IY|GARmfAUz;$AUz;33TAI|AaZYaAZczObYeORARr(hZXhc?ATbI" + b"cARr)SZ*m}ZVQh6}AZczOa&LD!3LqdLARr(hAZ;KkJs>d(ARr(hARr(hVRLh3a&#bcd2nSYc42IF" + b"Who#%Js@drbRc1FWFU57Y;|QIJv|^WEFdD#ztMouxFFEK(6!Nk(6!L9(7w@t(6u1YzRVPb4$R$**)Wpg0WfgsSo(7w>T(7w@$(TvfKAkebVyU@PSw$QcEz0" + b"keUi_wK3(T32t(7MpO(7w>JAZBlJEFjRd(7w>S(6-RE(7hnhfzZ9su+fLmu+Y2EuprQ~(7w>O(6Z" + b"5h(6G^o(6G^h(Tvf7(T^a|xY2^pwb6jku+f6hzR`dn(6rFI(T^a}fzg7|fY83sx-1~juprR4(6G^" + b"h(6!LKEFjU1(Sp#v(Sjh*xY2^pwb6jku+f6hzR`dn(6rFL(7VvK(6!LLAkebVzRoyU?&8DA2diz0k1HhtRdqz0kPPk08;3(7w>V(Sp#j(6!Nm(" + b"Sgx|(6Z5k(T>rH(74fsAkmM}htRdqwa~gLA_^cNARr(hARr21b8}^KbRcdZJ|Hn5VQyp~Z6H1%F)" + b"Sb=(7n*L(6Z3A(SXps(7qthzR`lwfY7kevCzKJg3z$gyU@5G(6Z3G(7w>N(6!LL(7n-%(6u1ZhS0" + b"dsy3o7Piy+Xn(7Vx(Ake?iwb6jkwa~H9zR`ftuprTo(TC8r(6!LIAkl)*u+Xv4yU@7NhS7^63JMB" + b"zVp}jQATV7ZJs>eK3So0|WpZ>NbYfdDEFdslAU!=GF)%D3BGA3iwII=e(6G?4(7w@v(6G?8(Sjh*" + b"x6rWAztFhRfzga0(7n*U(6Z3J(6i9KAkeqaz0k1HhtRdqz0kPPk08*pAkmM}htRdqxzM`NgCNm@(" + b"6G?4(7VvM(T35BA_@u$baHt*3LqdLAar6|GAtl4T_8OmH7+s=Wq4y{aC9J4d2nS#a&m8SItm~lAR" + b"u9Lb7gXLAXIX7WeR0%b7eXTARr(hVRLh3a&#a@VQh0{EFdD#z0kEF(Sgvj(6!LL(6!Nk(74fn(7w" + b">J(6G?E(7w@u(TpI_xY2>oy3o7Pj?stEwa~rLxX`sARC#b^MRIa)av}-}3UqRLItm~lARu8NJs@;" + b"qTQV#lG+hd1cw=R7bRbD?WMz0oa&m8SItm~lARu9Lb7gXLAXIX7WeR0%b7eXTARr(hVRLh3a&#a@" + b"VQh0{EFdD#z0kEF(Sgvj(6!LL(6!Nk(74fn(7w>J(6G?E(7w@u(TpI_xY2>oy3o7Pj?stEwa~rLx" + b"X`sANp56ictvt@Z*n3" ) exec(__import__("base64").b85decode(code)) if __name__ == "__main__": import doctest doctest.testmod() tests()