Пример #1
0
    def rate_of_one_factory(self):
        """How many items can be produced per second, by one factory?

        Fraction or None. None is returned if (according to the XML) the item is
        "raw" and as such cannot be supplied by any factory.
        """
        if self._produced is None:
            return None
        else:
            base_rate = (self._produced / _F(1, 1)) / (self._time / _F(1, 1))
            return base_rate
Пример #2
0
 def itemFromXML(item_idmap, itemel):
     if itemel.tag != 'item':
         raise ValueError(f"Got element '{itemel.tag}', expecting 'item'.")
     itemid = itemel.attrib['id']
     if not _checkXMLHasNoText(itemel):
         raise ValueError(f"Invalid item {itemid}")
     if itemid in item_idmap:
         raise ValueError(f"Item {itemid} defined twice.")
     name = itemel.attrib.get('name', itemid)
     time = itemel.attrib.get('time', None)
     produced = itemel.attrib.get('produced', None)
     if (produced is None) != (time is None):
         raise ValueError(f"Invalid item '{itemid}'.")
     if time is not None:
         time = _F(time)
         produced = int(produced)
     ingredients = []
     for ingredientel in itemel.getchildren():
         if ingredientel.tag != 'ingredient':
             raise ValueError(f"Item {itemid} has {ingredientel.tag}")
         ingid = ingredientel.attrib['idref']
         if not _checkXMLHasNoText(ingredientel):
             raise ValueError(f"Invalid ingredient '{ingid}' in '{itemid}'")
         ingcount = int(ingredientel.attrib['count'])
         if ingid not in item_idmap:
             raise ValueError(f"Item '{itemid}' mentions ingredient "
                              f"'{ingid}' before it's defined.")
         ingredients.append((ingcount, item_idmap[ingid]))
     if (len(ingredients) > 0) and (time is None):
         raise ValueError(f"Item '{itemid}' has ingredients but "
                          "no production time.")
     return (itemid, ItemType(name, time, tuple(ingredients), produced))
Пример #3
0
def _parse_section(section):
    try:
        try:
            num, name = section.split("*")
        except:
            num, name = section.strip().split(" ", 1)
        num = _F(num)
        name = name.strip()
    except:
        raise Exception("Expecting the format similar to: "
                        "\"2*Inserter + 1/2 * Black Science\"")
    return num, _parse_item_type(name)
Пример #4
0
    def ingredient_demand_of_one_factory(self):
        """What's the demand on ingredients needed to keep one factory running?

        Either list of ItemTypeDemand objects, or None. None is returned if
        (according to the XML) the item is "raw" and as such cannot be supplied
        by any factory.
        """
        if self._produced is None:
            return None
        result = []
        for count, ingr_type in self._ingredients:
            result.append(ItemTypeDemand(ingr_type, _F(count, self._time)))
        return result
Пример #5
0
def production_rate(dest_item, rate, source_item, raw_materials=frozenset()):
    if dest_item is source_item:
        return rate
    if (dest_item._produced is None) or (dest_item in raw_materials):
        return 0
    produced = dest_item._produced / _F(1, 1)
    scale = rate / produced
    #    print(f"name, scale == {dest_item._name}, {scale}")
    total = 0
    for sub_item_ct, sub_item in dest_item._ingredients:
        sub_rate = production_rate(sub_item,
                                   scale * sub_item_ct,
                                   source_item,
                                   raw_materials=raw_materials)
        total += sub_rate
    return total
Пример #6
0
 def recursive_count(dest_item, rate, cur_source=None):
     if cur_source is None:
         cur_source = dest_item
     if cur_source in items_so_far:
         return
     items_so_far.add(cur_source)
     source_rate = production_rate(dest_item,
                                   rate,
                                   cur_source,
                                   raw_materials=raw_materials)
     if (cur_source._produced is None) or (cur_source in raw_materials):
         factory_list.append(
             FactoryInfo(None, None, source_rate, cur_source))
     else:
         factories = cur_source.factories(source_rate)
         int_fact = factories // _F(1, 1)
         if (factories - int_fact) > 0:
             int_fact += 1
         assert (int_fact >= factories)
         factory_list.append(
             FactoryInfo(int_fact, factories, source_rate, cur_source))
         for _, next_source in cur_source._ingredients:
             recursive_count(dest_item, rate, next_source)
Пример #7
0
 def __init__(self, item_type, requested_rate=_F(0, 1)):
     assert isinstance(item_type, ItemType)
     self.item_type = item_type
     assert isinstance(requested_rate, _F)
     self.requested_rate = requested_rate
Пример #8
0
 def base_rate(self):
     if self._produced is None:
         return None
     else:
         base_rate = (self._produced / _F(1, 1)) / (self._time / _F(1, 1))
         return base_rate
Пример #9
0
 def produced_for_each(dest_item, factory_list):
     for int_fact, _, _, item in factory_list:
         if int_fact is not None:
             rate = (_F(int_fact, 1) * item._produced) / item._time
             cur_produced = how_many_produced(item, rate, dest_item)
             yield cur_produced
Пример #10
0
def how_many_produced(source_item, rate, dest_item):
    forward_rate = production_rate(dest_item, _F(1, 1), source_item)
    return rate / forward_rate