In an allotment, a piece of land is divided in various lots that each have a different owner. Farmers used to have small pieces of land, that were often intertwined. Back then, a farmer had to walk or drive through the land of another farmer in order to reach his own lots. Today, because of the expansion in agriculture, square lots are used, and farmers strive to work with parcels that are as large as possible: rectangular areas of adjacent lots.
The example below shops a rectangular piece of land that was divided in $$10 \times 10$$ square lots. Three parcels (white triangles) are already taken into use by farmers. Search the surface of the largest possible parcel of which no lots are being used. In this example, this is a parcel that consists of 16 lots, as indicated by the striped rectangle.
Define a class Allotment with the following methods:
An initializing method __init__ with which an allotment can be made out of a rectangular piece of land. This allotment consists of a $$m \times n$$ grid of lots, with $$m$$ the number of rows and $$n$$ the number of columns in the grid. The values $$m$$ and $$n$$ must be given to the initializing method as arguments. Initially, there are no reserved lots (appointed to an owner).
A method __str__ with which the current reservations of the lots from the allotment can be given. No arguments can be given to this method. A reserved lot is indicated with a hyphen (-). A lot that has not yet been reserved, is indicated with a hash (#). Below you will find some examples of how the entire allotment should be printed.
A method reserve with which a rectangular parcel can be reserved. This method has four parameters, to which integers can be given. The first two parameters represent the row number and the column number of the position of the left upper corner of the parcel, and are obligatory. The last two parameters are optional, and represent the row number and the column number of the position of the right lower corner of the parcel. If these last parameters are not given, the parcel consists of only one lot, of which the position is is indicated by the first two parameters. As indicated in the image above, the rows are numbered from top to bottom and the columns from left to right, each starting from zero. If the parcel contains lots that have already been reserved, no lots must be reserved, and the method must raise an AssertionError as illustrated in the example below.
A method largestParcel that prints the size of the largest parcel that can still be reserved. I.e. this is the size of the largest rectangular area that consists of lots that have not yet been reserved. No arguments can be given to this method.
>>> allotment = Allotment(6, 6)
>>> print(allotment)
######
######
######
######
######
######
>>> allotment.largestParcel()
36
>>> allotment.reserve(3, 0, 5, 2)
>>> print(allotment)
######
######
######
---###
---###
---###
>>> allotment.largestParcel()
18
>>> allotment.reserve(0, 3, 2, 5)
>>> print(allotment)
###---
###---
###---
---###
---###
---###
>>> allotment.largestParcel()
9
>>> allotment.reserve(2, 2, 3, 3)
Traceback (most recent call last):
AssertionError: parcel can not be reserved
>>> print(allotment)
###---
###---
###---
---###
---###
---###