3. Read job shop records and checks
A job shop input gives a job count and a machine count. Each job then has one operation per machine. An operation is a pair: machine number and duration. Machine numbers start at 0.
Build on repeats and sections. All commands run from the repository root.
Read nested records
Section titled “Read nested records”Use an outer repeat for jobs and an inner repeat for operations. as jobs
names the list of job records; each job names an individual job for later
checks. The inner names play the same roles for operations.
n_jobs: 1..n_machines: 1..repeat n_jobs as jobs { each job repeat n_machines as steps { each step machine: 0..<n_machines duration: 0.. }}2 20 3 1 21 4 0 1iris read site/examples/tutorial/jobshop-records.iris site/examples/tutorial/jobshop.txt --dznn_jobs = 2;
n_machines = 2;
machine = [| 0, 1
| 1, 0 |];
duration = [| 3, 2
| 4, 1 |];
Each repeat adds one array level. machine and duration therefore have
depth 2. Row 0 holds job 0’s operations; row 1 holds job 1’s. The names jobs,
job, steps and step describe records and create no data entries.
0..<n_machines excludes its upper bound; 0.. admits nonnegative durations.
Ordinary numeric reads cross line breaks, so the pairs need not be laid out
on physical job lines. See
logical records.
Check each job and the whole instance
Section titled “Check each job and the whole instance”The range admits each machine number on its own. To require that a job uses
every machine exactly once, also check that its machine numbers are distinct:
with exactly n_machines operations, all in range, distinct numbers cover
every machine.
n_jobs: 1..n_machines: 1..check n_jobs <= (gecode.int_max - 2) / 2 / n_machines "there are too many jobs and machines"repeat n_jobs as jobs { each job repeat n_machines as steps { each step machine: 0..<n_machines duration: 0.. }}check distinct(job.machine) "a job uses a machine twice; each job must use every machine once"check sum(j in jobs: sum(j.duration)) <= gecode.int_max "the total duration is too large"2 20 3 1 21 4 0 1iris read site/examples/tutorial/jobshop-checks.iris site/examples/tutorial/jobshop.txt --dznn_jobs = 2;
n_machines = 2;
machine = [| 0, 1
| 1, 0 |];
duration = [| 3, 2
| 4, 1 |];
check distinct(job.machine) ranges over jobs. Within one job, job.machine
is the array of its machine numbers. The final check uses a comprehension to
sum durations across all jobs, then compares the total with Gecode’s integer
limit. The early count check is the library’s bound on the job/machine product.
A duplicate machine is in range but fails the record check:
2 20 3 0 21 4 0 1iris read site/examples/tutorial/jobshop-checks.iris site/examples/guides/jobshop-invalid.txt --dznsite/examples/guides/jobshop-invalid.txt:2:1: check failed for record 1 of 'jobs': a job uses a machine twice; each job must use every machine once
2 | 0 3 0 2
| ^
spec: site/examples/tutorial/jobshop-checks.iris:12
The diagnostic names the first job and points at the position where that job’s record started. This is E-CHECK-FAILED. See the records and checks guide and the Specification’s record access and failure witnesses.
Finish with the library reader
Section titled “Finish with the library reader”Real OR-Library and JSPLIB files include descriptions, separators and sometimes
several named instances. The library wraps the reader in instances, skips
# and +++ comments, and uses sections skip other to find the counts.
The count arm is last: its body reads the jobs, then sections end before
the next instance’s header.
format jobshop
comment "#" "+++"instances { sections skip other { "instance {name:word}" optional "{n_jobs:1..} {n_machines:1..}" last { check n_jobs <= (gecode.int_max - 2) / 2 / n_machines "there are too many jobs and machines"
repeat n_jobs as jobs { each job repeat n_machines as steps { each step machine: 0..<n_machines duration: 0.. } } } }
check distinct(job.machine) "a job uses a machine twice; each job must use every machine once" check sum(j in jobs: sum(j.duration)) <= gecode.int_max "the total duration is too large"}Hand-made OR-Library style file+++++++++++++++++++++++++++++instance handmade-or+++++++++++++++++++++++++++++Three jobs on three machines3 30 2 1 3 2 11 1 2 4 0 22 3 0 1 1 2iris read formats/jobshop/jobshop.iris formats/jobshop/cases/or-library/input.txt --dzn --param instance=handmade-orname = "handmade-or";
n_jobs = 3;
n_machines = 3;
machine = [| 0, 1, 2
| 1, 2, 0
| 2, 0, 1 |];
duration = [| 2, 3, 1
| 1, 4, 2
| 3, 1, 2 |];
The instance parameter selects handmade-or by name. An instances block
must be the final statement, so the checks stay inside it. Use the
several instances guide for catalogs and selection rules.
You now have the complete job shop library reader. Use the guides to adapt these structures to another format, and check and read samples as you make changes.