foop
Version:
interfaces that describe their intentions.
47 lines (41 loc) • 1.27 kB
JavaScript
// https://github.com/andrewplummer/Sugar/blob/master/lib/common.js#L766
function iterateWithCyclicCheck(obj, sortedKeys, stack, fn) {
function next(val, key) {
var cyc = false
// Allowing a step into the structure before triggering this check to save
// cycles on standard JSON structures and also to try as hard as possible to
// catch basic properties that may have been modified.
if (stack.length > 1) {
var i = stack.length
while (i--) {
if (stack[i] === val) {
cyc = true
}
}
}
stack.push(val)
fn(key, val, cyc, stack)
stack.pop()
}
function iterateWithSortedKeys() {
// Sorted keys is required for serialization, where object order
// does not matter but stringified order does.
var arr = getKeys(obj).sort(), key
for (var i = 0; i < arr.length; i++) {
key = arr[i]
next(obj[key], arr[i])
}
}
// This method for checking for cyclic structures was egregiously stolen from
// the ingenious method by @kitcambridge from the Underscore script:
// https://github.com/documentcloud/underscore/issues/240
if (!stack) {
stack = []
}
if (sortedKeys) {
iterateWithSortedKeys()
}
else {
forEachProperty(obj, next)
}
}