I am writing because I have a discrete optimization problem which I have to solve, and I think there might be already some theoretical results or even libraries in Python implementing it (such as OR-Tool from Google).
The problem is the following: I have different objects that are printed using different molds. You can think of objects being little soldiers or anything else. There is a different mold for every kind of object. In total, I have 3 different printers, 2 of which can use (at the same time) 8 molds and 1 which can use 10 molds. When an order for different objects arrives, I have to print all of them trying to minimize the number of prints. There is another side-constraint, which is very important, but which does not have to enter directly the theoretical formulation of the problem: every time I change the molds, I have a huge loss of the printing mater
ial. Therefore, minimizing the number of mold replacements is even more relevant than minimizing the number of prints (in other words, it is better to print more times than required the same objects, if I may change the molds one time less).
Here is an example which might help the comprehension:

Orders:

Object A: 80
Object B: 95
Object C: 101
….
Object Z: 71


Molds:

A: 1
B: 2
C: 3
….
Z: 1


Available printers (quantity of molds they handle):

P1: 8
P2: 8
P3 10



Note: a printer always need to be fully loaded with molds.
I thought of a simple algorithm to arrive to a solution for a single printer, exploiting the ratio order/number_of_molds per each object, but I am confident there is something better, even to consider multiple “printer” at the same time. In some sense, it is similar to a bin-packing problem, but it is a bit more complex, with more conditions.
My thoughts about this are as follows. Prints are (partially) wasted if for any molt (but not all) mounted to a printer the ordered amount of objects is exceeded. This happens if the number of ordered objects for molts mounted to the same printer is not equal.
The first step of optimization is therefore to build groups of 8 or 10 molts with a similar amount of ordered objects. Let's keep it simple first and only take groups of 8 into account and forget about the third printer.
The sum of wasted prints is the sum of the differences between the largest number of orders and the lowest number of orders within each group.
We can optimize this number by splitting the number of orders across the available molts (if more than one). For simplicity, let's forget for the moment that we could split the number also by using the same molt again in a different setup. This gives us M-1 degrees of freedom for each type of molt which we can use to minimize the number of wasted prints (M is the number of molts available).
This is far from a complete solution but might be a starting point.
Optimizing combination and number of prints based on order, molds