, 스트레이트 아웃 비교는 O (n), 한 배열의 각 요소를 다른 배열의 모든 요소와 비교해야합니다.
개체가 비슷한 경우 적절한 비교 함수를 사용하여 항목을 정렬 한 다음 두 요소가 동시에 적게 있는지 확인하면서 두 배열을 동시에 반복 할 수 있습니다. 병합 정렬에 익숙하다면 병합 단계와 매우 유사합니다. 비교 함수가 O (1)이고 정렬이 O (n log (n))이고 합병 유사 비교 루프가 O (n)이고 총 시간 복잡도가 O (n log 여기서 "n"은 더 큰 배열의 길이입니다.
imagesInUploadsFolder.sort(imgCmp);
imagesInDatabaseTable.sort(imgCmp);
// diff will hold the difference of the arrays
var diff = [];
var i=0, j=0, cmp;
while (i < imagesInUploadsFolder.length && j < imagesInDatabaseTable.length) {
cmp = cmp(imagesInUploadsFolder[i], imagesInDatabaseTable[j]);
if (cmp < 0) {
// up[i] < db[j]
++i;
diff.append(imagesInUploadsFolder[i]);
} else if (cmp > 0) {
// up[i] > db[j]
++j;
diff.append(imagesInDatabaseTable[j]);
} else {
// up[i] == db[j]
++i; ++j;
}
}
// one of the arrays may still have items; if so, loop over it and add the items
if (i < imagesInUploadsFolder.length) {
for (; i < imagesInUploadsFolder.length; ++i) {
diff.append(imagesInUploadsFolder[i]);
}
} else if (j < imagesInDatabaseTable.length)) {
for (; i < imagesInDatabaseTable.length; ++i) {
diff.append(imagesInDatabaseTable[i]);
}
}
// diff now holds items that are in only one of the two arrays.
는 적합한 object ID function를 정의 할 경우, 요소들의 세트를 유지하는 보조 데이터 구조를 생성 할 수있다. 객체 속성에 접근하는 것이 O (f (n))이면 (해시 f = 1, 균형 잡힌 나무 f = log (n)),이 접근법은 O (n * f (n))이므로, 정렬 - 비교 접근법보다 더 복잡하지 않습니다. 테스트되지 않은 비효율적 구현 :
는 노동 조합과 배열의 차이를 모두 원하는 경우
function Set(from) {
this.elements = {};
this.size = 0;
if (from) {
for (var i=0; i < from.length) {
this.add(from[i]);
}
}
}
Set.prototype.each = function(f) {
var eltId;
foreach (eltId in this.elements) {
f(this.elements[eltId], eltId);
}
};
Set.prototype.clone = function() {
var clone = new Set();
this.each(function(obj, id) {
clone.add(obj);
});
return clone;
};
Set.prototype.contains = function(obj) {
return obj.uniqueId() in this.elements;
};
Set.prototype.add = function(obj) {
var objId = obj.uniqueId();
if (! (objId in this.elements)) {
++this.size;
this.elements[objId] = obj;
}
return this;
};
Set.prototype.remove = function(obj) {
var objId = obj.uniqueId();
if (objId in this.elements) {
--this.size;
delete this.elements[objId];
}
return this;
};
Set.prototype.union = function(other) {
other.each(function(elt, id) { this.add(elt); });
return this;
};
Set.prototype.sub = function(other) {
other.each(function (elt, id) {
this.remove(elt);
});
return this;
};
Set.prototype.diff = function(other) {
var mine = this.clone();
mine.sub(other);
var others = other.clone();
others.sub(this);
mine.union(others);
return mine;
};
Set.prototype.toArray = function(obj) {
var arr = [];
this.each(function(elt, id) {
arr.append(elt);
});
return arr;
};
var uploadsSet = new Set(imagesInUploadsFolder),
dbSet = new Set(imagesInDatabaseTable),
imagesInJustOne = uploadsSet.diff(dbSet);
, 당신은보다 효율적으로 대신 별도 Set.diff
및 Set.union
을 사용을 계산하는 Set
에 적합한 방법을 정의 할 수 있습니다.
분명히 비교를 위해'==='연산자를 사용하고 싶습니다 ... –