View difference between Paste ID: VLYtv7RZ and ak2UXkuB
SHOW: | | - or go back to the newest paste.
1
-- BeeAlverizer 1 fork of BeeAnalyzer 4
2
-- Original code by Direwolf20
3
-- Hotfix 1 by Mandydax
4
-- Hotfix 2 by Mikeyhun/MaaadMike
5
6
-- Major overhaul to make work without turtle by Damaged
7
8
-- JSON lib loaded to debug arrays
9
local JSON = (loadfile "JSON.lua")()
10
JSON.strictTypes = true
11
12
13
-- Direction definitions.
14-
local allBeeData = {}
14+
15
16
17-
analyzer = peripheral.wrap("left")
17+
18
19
20-
function getCountInMemoryChest(i)
20+
21-
   local inventoryQuantity
21+
22-
   if not memoryChest.getStackInSlot(i) then
22+
23-
      inventoryQuantity = 0
23+
24
25-
      invenotryQuantity = memoryChest.getStackInSlot(i)["qty"]
25+
26
27-
   return invenotryQuantity
27+
28
29
local princessSlot = 0
30
alveary = peripheral.wrap("back")
31
memoryChest = peripheral.wrap("top")
32
local maxMem = memoryChest.getInventorySize()
33
-- Fix for some versions returning bees.species.*
34
function fixName(name)
35
   return name:gsub("bees%.species%.",""):gsub("^.", string.upper)
36
end
37
38
function getBeeData(i)
39
   return memoryChest.getStackInSlot(i)["beeInfo"]
40
end 
41
42
function getPrimarySpecies(i)
43
   if getBeeData(i)["speciesPrimary"] then
44
      return fixName(getBeeData(i)["speciesPrimary"])
45
   else
46
      return fixName(getBeeData(i)["active"]["species"])
47
   end
48
end
49
50
function getSecondarySpecies(i)
51
   if getBeeData(i)["speciesSecondary"] then
52
      return fixName(getBeeData(i)["speciesSecondary"])
53
   else
54
      return fixName(getBeeData(i)["inactive"]["species"])
55
   end
56
end
57
58
scoresFertility = {
59
   [1] = 0.1,
60
   [2] = 0.2,
61
   [3] = 0.3,
62
   [4] = 0.4
63
}
64
scoresSpeed = {
65
   ["0.3"] = 0.01, -- Slowest
66
   ["0.6"] = 0.02, -- Slower
67
   ["0.8"] = 0.03, -- Slow
68
   ["1"]   = 0.04, -- Normal
69
   ["1.2"] = 0.05, -- Fast
70
   ["1.4"] = 0.06, -- Faster
71
   ["1.7"] = 0.07  -- Fastest
72
}
73
scoresAttrib = {
74
   diurnal       = 0.004,
75
   nocturnal     = 0.003,
76
   tolerantFlyer = 0.002,
77
   caveDwelling  = 0.0001
78
}
79
scoresTolerance = {
80
   ["NONE"]   = 0.00000,
81
   ["UP 1"]   = 0.00001,
82
   ["UP 2"]   = 0.00002,
83
   ["UP 3"]   = 0.00003,
84
   ["UP 4"]   = 0.00004,
85
   ["UP 5"]   = 0.00005,
86
   ["DOWN 1"] = 0.00001,
87
   ["DOWN 2"] = 0.00002,
88
   ["DOWN 3"] = 0.00003,
89
   ["DOWN 4"] = 0.00004,
90
   ["DOWN 5"] = 0.00005,
91
   ["BOTH 1"] = 0.00002,
92
   ["BOTH 2"] = 0.00004,
93
   ["BOTH 3"] = 0.00006,
94
   ["BOTH 4"] = 0.00008,
95
   ["BOTH 5"] = 0.00010
96
}
97
98
-- the bee graph ---------------------------------------------------------------
99
100
bees = {}
101
102
function addParent(parent, offspring)
103
   if bees[parent] then
104
      bees[parent].mutateTo[offspring] = true
105
      else
106
      bees[parent] = {
107
         --name = parent,
108
         score = nil,
109
         mutateTo = {[offspring]=true},
110
         mutateFrom = {}
111
      }
112
   end
113
end
114
115
function addOffspring(offspring, parentss)
116
   if bees[offspring] then
117
      for i, parents in ipairs(parentss) do
118
         table.insert(bees[offspring].mutateFrom, parents)
119
      end
120
      else
121
      bees[offspring] = {
122
         score = nil,
123
         mutateTo = {},
124
         mutateFrom = parentss
125
      }
126
   end
127
   for i, parents in ipairs(parentss) do
128
      for i, parent in ipairs(parents) do
129
         addParent(parent, offspring)
130
      end
131
   end
132
end
133
134
-- score bees that have no parent combinations as 1
135
-- iteratively find the next bee up the line and increase the score
136
function scoreBees()
137
   -- find all bees with no mutateFrom data
138
   local beeCount = 0
139
   local beeScore = 1
140
   for name, beeData in pairs(bees) do
141
      if #beeData.mutateFrom == 0 then
142
         beeData.score = beeScore
143
         else
144
         beeCount = beeCount + 1
145
      end
146
   end
147
   while beeCount > 0 do
148
      beeScore = beeScore * 2
149
      -- find all bees where all parent combos are scored
150
      for name, beeData in pairs(bees) do
151
         if not beeData.score then
152
            local scoreBee = true
153
            for i, beeParents in ipairs(beeData.mutateFrom) do
154
               local parent1 = bees[beeParents[1]]
155
               local parent2 = bees[beeParents[2]]
156
               
157
               if not parent1.score
158
                  or parent1.score == beeScore
159
                  or not parent2.score
160
                  or parent2.score == beeScore then
161
                  scoreBee = false
162
                  break
163
               end
164
            end
165
            if scoreBee then
166
               beeData.score = beeScore
167
               beeCount = beeCount - 1
168
            end
169
         end
170
      end
171
   end
172
end
173
174
-- produce combinations from 1 or 2 lists
175
function choose(list, list2)
176
   local newList = {}
177
   if list2 then
178
      for i = 1, #list2 do
179
         for j = 1, #list do
180
            if list[j] ~= list[i] then
181
               table.insert(newList, {list[j], list2[i]})
182
            end
183
         end
184
      end
185
      else
186
      for i = 1, #list do
187
         for j = i, #list do
188
            if list[i] ~= list[j] then
189
               table.insert(newList, {list[i], list[j]})
190
            end
191
         end
192
      end
193
   end
194
   return newList
195
end
196
197
198
for key, value in pairs (alveary.getBeeBreedingData()) do
199
   addOffspring( fixName(value.result), {{ fixName(value.allele1), fixName(value.allele2) }} )
200
end
201
scoreBees()
202
203
-- logging ---------------------------------------------------------------------
204
205
local logFile = fs.open("bee.log", "w")
206-
   for i = 1,9 do
206+
207
   msg = msg or ""
208
   logFile.write(tostring(msg))
209
   logFile.flush()
210
   io.write(msg)
211-
      analyzer.pushItem("up",i)
211+
212
function logLine(msg)
213
   msg = msg or ""
214
   logFile.write(msg.."\n")
215
   logFile.flush()
216
   io.write(msg.."\n")
217
end
218-
   while not not alveary.getStackInSlot(1) do
218+
219
function logTable(table)
220
   for key, value in pairs (table) do
221
      logLine(key .. " = " .. tostring(value))
222
   end
223-
   for i = 3,9 do 
223+
224-
      if memoryChest.pullItem("north",i) then
224+
225-
         log("*")
225+
226
-- analyzing functions ---------------------------------------------------------
227
228
function clearSystem()
229
   -- clear out alveary
230
   for i = 2,9 do
231
      memoryChest.pullItem("north",i)
232
   end
233
   -- clear out analyzer
234
   for i = 1, 12 do
235
      memoryChest.pullItem("west",i)
236
   end
237-
      if not ( data.rawName == "item.beeprincessge" or data.rawName == "item.beequeenge" or data.rawName == "item.beedronege" ) then
237+
238
239
function getBees()
240
   -- get bees from apiary
241
   log("waiting for bees.")
242
   while true do
243
      local gotStuff = false
244
      for i = 3,9 do
245-
            print("Analyzing: ".. i)
245+
         if memoryChest.pullItem("north",i) ~= 0 then
246-
            analyzer.pullItemIntoSlot("up",i,64,3)
246+
            gotStuff = true
247-
            while analyzer.pushItem("up",9,61,i) == 0 do sleep(1) end
247+
248-
            data = memoryChest.getStackInSlot(i)
248+
249
      if gotStuff == true then
250-
         -- Check if it's a drone or princess
250+
251-
         allBeeData[i] = {}
251+
252-
         if string.find(data.rawName, "princess") then
252+
253-
            allBeeData[i]["type"] = "princess"
253+
254
   end
255-
            allBeeData[i]["type"] = "drone"
255+
256-
         end               
256+
257-
         -- Active values
257+
258-
         for key, value in pairs (data.beeInfo.active) do
258+
259-
            if key == "species" then
259+
260-
               allBeeData[i]["speciesPrimary"] = value
260+
261-
            else
261+
262-
               allBeeData[i][key] = value
262+
263
   local highestScore
264
   local highestScoreDrone
265-
         -- Inactive values
265+
266-
         allBeeData[i]["speciesSecondary"] = data.beeInfo.inactive.species
266+
      data = memoryChest.getStackInSlot(i) 
267-
         allBeeData[i]["speciesPrimary"] = fixName(allBeeData[i]["speciesPrimary"])
267+
      if not ( string.find(data["rawName"], "item.beedrone") or string.find(data["rawName"], "item.beeprincess") ) then
268-
         allBeeData[i]["speciesSecondary"] = fixName(allBeeData[i]["speciesSecondary"])
268+
269-
         if allBeeData[i]["type"] == "princess" then
269+
270
      else
271
         print("B")
272
         --print(JSON:encode(data["beeInfo"]))
273
         --print(data["beeInfo"]["isAnalyzed"]) 
274
         if data["beeInfo"]["isAnalyzed"] == false then
275
            memoryChest.pushItemIntoSlot("west",i,64,3)
276-
      -- check for untargeted species
276+
            while memoryChest.pullItemIntoSlot("west",9,61,i) == 0 do sleep(1) end
277-
      if allBeeData[i] and (not bees[allBeeData[i]["speciesPrimary"]].targeted or not bees[allBeeData[i]["speciesSecondary"]].targeted) then
277+
278
         if string.find(data["rawName"], "princess") then
279-
         allBeeData[i] = nil
279+
280
               memoryChest.swapStacks(i,1)
281
            end
282
            princessSlot = 1
283-
   if princessSlot > 0 then
283+
284
         -- check for untargeted species
285-
      for i = 2, memoryChest.getInventorySize() do
285+
         if memoryChest.getStackInSlot(i) ~= nil and (not bees[getPrimarySpecies(i)].targeted or not bees[getSecondarySpecies(i)].targeted) then
286-
         if not allBeeData[i] then
286+
            memoryChest.pushItem("east",i)
287-
            for j = i + 1, memoryChest.getInventorySize() do
287+
288-
               if allBeeData[j] then
288+
289-
                  memoryChest.swapStacks(i, j)
289+
290-
                  allBeeData[i], allBeeData[j] = allBeeData[j], allBeeData[i]
290+
291
   if princessSlot == 1 then
292
      logLine("compacting drones...")
293
      for i = 2, maxMem do
294
         if memoryChest.getStackInSlot(i) == nil then
295
            for key,data in pairs(memoryChest.getAllStacks()) do
296
               if key > i then
297
                  memoryChest.swapStacks(i, key)
298-
      for i = 2, memoryChest.getInventorySize() do
298+
299-
         highestScore = i
299+
300-
         if allBeeData[i] then
300+
301-
            allBeeData[i].score = scoreBee(allBeeData[princessSlot], allBeeData[i])
301+
302-
            for j = i + 1, memoryChest.getInventorySize() do
302+
303-
               if allBeeData[j] then
303+
304-
                  if not allBeeData[j].score then
304+
305-
                     allBeeData[j].score = scoreBee(allBeeData[princessSlot], allBeeData[j])
305+
      for i = 2, maxMem do
306
         highestScoreDrone = i
307-
                  if allBeeData[j].score > allBeeData[highestScore].score then
307+
         if memoryChest.getStackInSlot(i) ~= nil then
308-
                     highestScore = j
308+
            highestScore = scoreBee(i)
309
            for key,data in pairs(memoryChest.getAllStacks()) do
310
               if key > 2 then
311
                  if scoreBee(key) > highestScore then
312
                     highestScoreDrone = key
313-
            if highestScore ~= i then
313+
314-
               memoryChest.swapStacks(i, highestScore)
314+
315-
               allBeeData[i], allBeeData[highestScore] = allBeeData[highestScore], allBeeData[i]
315+
316
            -- swap bees
317
            if highestScoreDrone ~= i then
318
               memoryChest.swapStacks(i, highestScoreDrone)
319
            end
320-
      allBeeData[princessSlot].slot = 1
320+
321-
      printBee(allBeeData[princessSlot])
321+
322-
      for i = 2, memoryChest.getInventorySize() do
322+
323-
         if allBeeData[i] then
323+
      for i = 1, maxMem do
324-
            allBeeData[i].slot = i
324+
         if memoryChest.getStackInSlot(i) ~= nil then
325-
            printBee(allBeeData[i])
325+
            printBee(i)
326
         end
327
      end
328
   end
329
   logLine()
330
end
331
332-
function scoreBee(princessData, droneData)
332+
function scoreBee(droneID)
333-
   local droneSpecies = {droneData["speciesPrimary"], droneData["speciesSecondary"]}
333+
   local beeDataDrone = getBeeData(droneID)
334
   local beeDataPrincess = getBeeData(princessSlot)
335
   local droneSpecies = {getPrimarySpecies(droneID), getSecondarySpecies(droneID)}
336
   -- check for untargeted species
337
   if not bees[droneSpecies[1]].targeted or not bees[droneSpecies[2]].targeted then
338-
   local princessSpecies = {princessData["speciesPrimary"], princessData["speciesSecondary"]}
338+
339
   end
340
   local princessSpecies = {getPrimarySpecies(princessSlot), getSecondarySpecies(princessSlot)}
341
   local score
342
   local maxScore = 0
343
   for _, combo in ipairs({{princessSpecies[1], droneSpecies[1]}
344
      ,{princessSpecies[1], droneSpecies[2]}
345-
   -- find maximum score for each combo
345+
346-
   score = (bees[combo[1]].score + bees[combo[2]].score) / 2
346+
347
      -- find maximum score for each combo
348-
      if beeData.targeted then
348+
      score = (bees[combo[1]].score + bees[combo[2]].score) / 2
349-
         for i, parents in ipairs(beeData.mutateFrom) do
349+
350-
            if combo[1] == parents[1] and combo[2] == parents[2]
350+
         if beeData.targeted then
351-
               or combo[2] == parents[1] and combo[1] == parents[2] then
351+
            for i, parents in ipairs(beeData.mutateFrom) do
352-
               score = (score + beeData.score) / 2
352+
               if combo[1] == parents[1] and combo[2] == parents[2]
353
                  or combo[2] == parents[1] and combo[1] == parents[2] then
354
                  score = (score + beeData.score) / 2
355
               end
356
            end
357-
   maxScore = maxScore + score
357+
358
      end
359
      maxScore = maxScore + score
360
   end
361
   -- add one for each combination that results in the maximum score
362-
   score = score + math.max(scoresFertility[droneData["fertility"]], scoresFertility[princessData["fertility"]])
362+
363-
   score = score + math.min(scoresSpeed[tostring(droneData["speed"])], scoresSpeed[tostring(princessData["speed"])])
363+
364-
   if droneData["nocturnal"] or princessData["nocturnal"] then score = score + scoresAttrib["nocturnal"] end
364+
   score = score + math.max(scoresFertility[beeDataDrone["active"]["fertility"]], scoresFertility[beeDataPrincess["active"]["fertility"]])
365-
   if droneData["tolerantFlyer"] or princessData["tolerantFlyer"] then score = score + scoresAttrib["tolerantFlyer"] end
365+
   score = score + math.min(scoresSpeed[tostring(beeDataDrone["active"]["speed"])], scoresSpeed[tostring(beeDataPrincess["active"]["speed"])])
366-
   if droneData["caveDwelling"] or princessData["caveDwelling"] then score = score + scoresAttrib["caveDwelling"] end
366+
   if beeDataDrone["active"]["nocturnal"] or beeDataPrincess["active"]["nocturnal"] then score = score + scoresAttrib["nocturnal"] end
367-
   score = score + math.max(scoresTolerance[string.upper(droneData["temperatureTolerance"])], scoresTolerance[string.upper(princessData["temperatureTolerance"])])
367+
   if beeDataDrone["active"]["tolerantFlyer"] or beeDataPrincess["active"]["tolerantFlyer"] then score = score + scoresAttrib["tolerantFlyer"] end
368-
   score = score + math.max(scoresTolerance[string.upper(droneData["humidityTolerance"])], scoresTolerance[string.upper(princessData["humidityTolerance"])])
368+
   if beeDataDrone["active"]["caveDwelling"] or beeDataPrincess["active"]["caveDwelling"] then score = score + scoresAttrib["caveDwelling"] end
369
   score = score + math.max(scoresTolerance[string.upper(beeDataDrone["active"]["temperatureTolerance"])], scoresTolerance[string.upper(beeDataPrincess["active"]["temperatureTolerance"])])
370
   score = score + math.max(scoresTolerance[string.upper(beeDataDrone["active"]["humidityTolerance"])], scoresTolerance[string.upper(beeDataPrincess["active"]["humidityTolerance"])])
371
   return score
372
end
373
374
function printHeader()
375
   logLine()
376
   logLine("sl t species f spd n f c tmp hmd score ")
377
   logLine("--|-|-------|-|---|-|-|-|---|---|------")
378
end
379
380
-- string constants for console output
381
toleranceString = {
382
   ["NONE"] = "  - ",
383
   ["UP 1"] = " +1 ",
384
   ["UP 2"] = " +2 ",
385
   ["UP 3"] = " +3 ",
386
   ["UP 4"] = " +4 ",
387
   ["UP 5"] = " +5 ",
388
   ["DOWN 1"] = " -1 ",
389
   ["DOWN 2"] = " -2 ",
390
   ["DOWN 3"] = " -3 ",
391
   ["DOWN 4"] = " -4 ",
392
   ["DOWN 5"] = " -5 ",
393
   ["BOTH 1"] = "+-1 ",
394
   ["BOTH 2"] = "+-2 ",
395
   ["BOTH 3"] = "+-3 ",
396
   ["BOTH 4"] = "+-4 ",
397
   ["BOTH 5"] = "+-5 "
398
}
399
400
speedString = {
401
   ["0.3"] = "0.3", -- Slowest
402
   ["0.6"] = "0.6", -- Slower
403
   ["0.8"] = "0.8", -- Slow
404
   ["1"]   = "1.0", -- Normal
405
   ["1.2"] = "1.2", -- Fast
406
   ["1.4"] = "1.4", -- Faster
407
   ["1.7"] = "1.7"  -- Fastest
408-
function printBee(beeData)
408+
409-
   log(beeData["slot"] < 10 and " "..beeData["slot"].." " or beeData["slot"].." ")
409+
410
function printBee(i)
411-
   log(beeData["type"] == "princess" and "P " or "D ")
411+
   local beeData = getBeeData(i)
412
   log(i < 10 and " "..i.." " or i.." ")
413-
   log(beeData["speciesPrimary"]:gsub("bees%.species%.",""):sub(1,3)..":"..beeData["speciesSecondary"]:gsub("bees%.species%.",""):sub(1,3).." ")
413+
414
   log(string.find(memoryChest.getStackInSlot(i)["rawName"], "princess") and "P " or "D ")
415-
   log(tostring(beeData["fertility"]).." ")
415+
416
   log(getPrimarySpecies(i):gsub("bees%.species%.",""):sub(1,3)..":"..getSecondarySpecies(i):gsub("bees%.species%.",""):sub(1,3).." ")
417-
   log(speedString[tostring(beeData["speed"])].." ")
417+
418
   log(tostring(beeData["active"]["fertility"]).." ")
419-
   log(beeData["nocturnal"] and "X " or "- ")
419+
420
   log(speedString[tostring(beeData["active"]["speed"])].." ")
421-
   log(beeData["tolerantFlyer"] and "X " or "- ")
421+
422
   log(beeData["active"]["nocturnal"] and "X " or "- ")
423-
   log(beeData["caveDwelling"] and "X " or "- ")
423+
424
   log(beeData["active"]["tolerantFlyer"] and "X " or "- ")
425-
   log(toleranceString[string.upper(beeData["temperatureTolerance"])])
425+
426
   log(beeData["active"]["caveDwelling"] and "X " or "- ")
427-
   log(toleranceString[string.upper(beeData["humidityTolerance"])])
427+
428
   log(toleranceString[string.upper(beeData["active"]["temperatureTolerance"])])
429-
   log(beeData.score and string.format("%5.1d", beeData.score).." " or "      ")
429+
430
   log(toleranceString[string.upper(beeData["active"]["humidityTolerance"])])
431
   -- score
432
   log(scoreBee(i) and string.format("%5.1d", scoreBee(i)).." " or "      ")
433
   logLine()
434
end
435-
   for i = ( memoryChest.getInventorySize() - 9 ), memoryChest.getInventorySize() do
435+
436
function dropExcess()
437
   logLine("dropping excess...")
438-
      allBeeData[i] = nil
438+
   for i = ( maxMem - 9 ), maxMem do
439
      -- drop drones over ( max inv - 9 ) to clear space for newly bred bees and product
440
      memoryChest.pushItem("east",i)
441
   end 
442-
function isPurebred(princessData, droneData)
442+
443
444-
   if princessData["speciesPrimary"] ~= princessData["speciesSecondary"] then
444+
function isPurebred(droneID)
445
   -- check if princess and drone are exactly the same and no chance for mutation
446
   if getPrimarySpecies(princessSlot) ~= getSecondarySpecies(princessSlot) then
447-
   for key, value in pairs(princessData) do
447+
448-
      if value ~= droneData[key] and key ~= "territory" and key ~= "type" and key ~= "slot" then
448+
449
   local droneData = getBeeData(droneID)
450
   local princessData = getBeeData(princessSlot)
451
   for i,key in pairs({ "fertility", "speed", "nocturnal", "tolerantFlyer", "caveDwelling", "temperatureTolerance", "humidityTolerance" }) do
452
      if
453
         droneData["active"][key] ~= princessData["active"][key] or
454
         droneData["inactive"][key] ~= princessData["inactive"][key]
455-
function getUnknown(princessData, droneData)
455+
      then
456-
   -- lists species that are not in the bee graph
456+
457-
   local unknownSpecies = {}
457+
458-
   if not bees[princessData["speciesPrimary"]] then
458+
459-
      table.insert(unknownSpecies, princessData["speciesPrimary"])
459+
460
--   for key, value in pairs(getBeeData(princessSlot)) do
461-
   if not bees[princessData["speciesSecondary"]] then
461+
--      if value ~= getBeeData(droneID)[key] and key ~= "territory" then
462-
      table.insert(unknownSpecies, princessData["speciesSecondary"])
462+
--      end
463
--   end
464-
   for _, beeData in pairs(droneData) do
464+
465-
      if not bees[beeData["speciesPrimary"]] then
465+
466-
         table.insert(unknownSpecies, beeData["speciesPrimary"])
466+
467
468-
      if not bees[beeData["speciesSecondary"]] then
468+
469-
         table.insert(unknownSpecies, beeData["speciesSecondary"])
469+
470
-- set species and all parents to targeted
471
function targetBee(name)
472-
   return unknownSpecies
472+
473
   if bee and not bee.targeted then
474
      bee.targeted = true
475
      for i, parents in ipairs(bee.mutateFrom) do
476
         for j, parent in ipairs(parents) do
477
            targetBee(parent)
478
         end
479
      end
480
   end
481
end
482
483
-- set bee graph entry to targeted if species was specified on the command line
484
-- otherwise set all entries to targeted
485
tArgs = { ... }
486
if #tArgs > 0 then
487
   logLine("targeting bee species:")
488
   for i, target in ipairs(tArgs) do
489
      targetBee(target)
490
      for name, data in pairs(bees) do
491
         if data.targeted and data.score > 1 then
492
            logLine(name .. string.rep(" ", 20-#name), data.score)
493
         end
494
      end
495
   end
496
   else
497
   for _, beeData in pairs(bees) do
498
      beeData.targeted = true
499
   end
500
end
501
502
-- breeding loop ---------------------------------------------------------------
503
504
logLine("Clearing system...")
505
clearSystem()
506
if not memoryChest.getAllStacks() then
507
   print("No bees to work on, add bees and restart")
508
else
509
   redstone.setOutput("bottom", true)
510
   while true do
511
      analyzeBees()
512
      if princessSlot == 1 then
513-
redstone.setOutput("bottom", true)
513+
         if isPurebred(2) then
514-
while true do
514+
            logLine("Bees are purebred")
515-
   analyzeBees()
515+
            redstone.setOutput("bottom", false)
516-
   if allBeeData[princessSlot] then
516+
            break
517-
      if isPurebred(allBeeData[princessSlot], allBeeData[2]) then
517+
518-
         logLine("Bees are purebred")
518+
         memoryChest.pushItemIntoSlot("north",1,1,1)
519-
         redstone.setOutput("bottom", false)
519+
         memoryChest.pushItemIntoSlot("north",2,1,2)
520
         dropExcess()
521
      end
522-
if true then break end
522+
      getBees()
523-
      memoryChest.pushItemIntoSlot("north",1,1,1)
523+
524-
      memoryChest.pushItemIntoSlot("north",2,1,2)
524+
525-
      allBeeData[1] = nil
525+