import random # jobScheduling3.py # # this is the same as jobScheduling2.py (and jobscheduling.py) except that it also works # correctly in the cases where the original two fail - that is, when some endpoint values # appear in more than one interval. # # For example, if you do: # ints = [[1,3], [2,5], [4,6], [2.1,6]] # # endsFirst(ints) will give the incorrect answer if using # the versions in jobScheduling.py and jobScheduling2.py # # The fix is simple: when filling the dictionary with interval data for right # endpoints, only add the new associated # Generates random intervals whose endpoints are in the range 0 through m (inclusive). # The endpoints are reals and it is guaranteed that the right endpoint of each interval # is at least as large as the left endpoint def generateIntervals(n, m): I = [] for i in range(0, n): x = [] x.append(random.uniform(0, m)) x.append(random.uniform(x[0], m)) I.append(x) return I # Takes a list of intervals as argument and creates a dictionary, whose keys # are the endpoints of the intervals. Each endpoint maps to (i) the interval # itself, (ii) whether or not the endpoint is a left endpoint or a # right endpoiont, and (iii) whether or not the interval is available for # being used in the solution. Initially, all intervals are available. def createDictionary(I): ptsToIntervals = {} for x in I: #ptsToIntervals[x[0]] = [x, "left"] if ((x[1] in ptsToIntervals) and (x[0] < ptsToIntervals[x[1]][0][0])): printNow("dictionary already has smaller interval with same right end.") printNow("Ignoring: " + str(x)) else: ptsToIntervals[x[1]] = [x, "right"] printNow(ptsToIntervals) for key in ptsToIntervals: printNow(key) return ptsToIntervals # Takes a list of intervals as argument and creates a sorted list of # endpoints of the intervals. def createEndPtList(I): E = [] for x in I: E.append(x[1]) E.sort() printNow(E) return E # Scans the endpoints in left to right order, stops at each right endpoint # and checks if corresponding interval is available, by checking if the # corresponding left endpoint is sufficiently to the right def endsFirst(I): E = createEndPtList(I) ptsToIntervals = createDictionary(I) S = [] minleft = -1; for pt in E: if((ptsToIntervals[pt][1] == "right")and(ptsToIntervals[pt][0][0] >= minleft)): S.append(ptsToIntervals[pt][0]) minleft = pt return S