VisualVM OQL : 2 개의 개체 ID에 대한 (간접적 인) 도달 / 참조가있는 객체 찾기?
문제
내 질문은 짧고 compact :
VisualVM이있는 두 개의 객체를 찾으면 어떤 종류의 OQL 쿼리를 수행 할 수있는 모든 오브젝트가있는 모든 오브젝트 또는이 두 오브젝트에 대한 참조를 찾을 수 있습니까?
JB 용 업데이트 :
코드를 편집 한 후 다음을 수행했습니다.
//QUERY SCRIPT: find object that (indirectly) references to all target objects
//list all objects that the objects we search for should (indirectly) refer to
var targetObjects = [ heap.findObject("811819664"), //eg. obj that contains a player's health
heap.findObject("811820024") //eg. obj that contains the same player's name
];
//list all objects here that every or most objects have as an indirect referer (eg. base class loaders)
var ignoreReferers = []; //eg. [heap.findObject("ignId1")];
//set array with all elements that refer to each target object
var targetObjectsReferers = [];
for (var tarObjIndex in targetObjects) {
var targetObjRefElements = [];
//get the live path of this target object
var livePaths = heap.livepaths(targetObjects[tarObjIndex]);
//cleanup every live path
for (var livePathsIndex in livePaths) {
var curLivePath = livePaths[livePathsIndex];
if ((curLivePath == null) || (curLivePath == "undefined")) continue;
//remove last element from live path as it is the actual object
curLivePath.pop();
//remove elements that equal an ignore referer object
for (var pathElementIndex in curLivePath) {
if ((curLivePath[pathElementIndex] == null) || (curLivePath[pathElementIndex] == "undefined")) continue;
for (var ignoreIndex in ignoreReferers) {
if (identical(curLivePath[pathElementIndex], ignoreReferers[ignoreIndex])) curLivePath.splice(pathElementIndex, 1); //FIXME: this might fail if index is not updated
}
}
}
//merge remaining life paths elements into targetObjRefElements
for (var livePathsIndex in livePaths) {
var curLivePath = livePaths[livePathsIndex];
for (var curLivePathIndex in curLivePath) {
targetObjRefElements.push(curLivePath[curLivePathIndex]);
}
}
//remove duplicate referers
targetObjRefElements = unique(targetObjRefElements, 'objectid(it)');
//add to target objects referers
targetObjectsReferers.push(targetObjRefElements);
}
//filter and return
filter(targetObjectsReferers[0], function(it1) {
var rslt = contains(targetObjectsReferers[1], function(it2) { //FIXME: this limits it to 2 objects!
return identical(it1, it2);
});
return rslt;
});
.
이 반환하면 해결하려는 잠시 후에 POP가 정의되지 않았습니다.내가 해결할 수있는 경우 예상 결과를 제공하는지 알 수 있습니다.
해결책
It sounds like you are trying to get all reference chains keeping your objects alive. You can use heap.livepaths(object) function to obtain them. You can take some hints from the following code
var paths1 = heap.livepaths(heap.findObject("1684177040")) // use the objectid of the first instance
var paths2 = heap.livepaths(heap.findObject("1684177160")) // use the objectid of the second instance
var pathArr1 = unique(rcs2array(paths1), 'objectid(it)') // flatten all the livepaths to a single array of instances
var pathArr2 = unique(rcs2array(paths2), 'objectid(it)') // the same for the second instance
// calculate the arrays' intersection - the result is the set of object keeping both of your instances alive
filter(pathArr1, function(it1) {
var rslt = contains(pathArr2, function(it2) {
return (objectid(it1) == objectid(it2))
})
return rslt
})
// helper function to convert an array of reference chains to a flat array of objects
function rcs2array(rcs) {
var arr = new Array()
for(var i=0;i<rcs.length;i++) {
var rc = rcs[i];
for(var j=0;j<rc.length;j++) {
arr.push(rc[j])
}
}
return arr
}
Please, bear in mind that this works only in VisualVM and jhat
제휴하지 않습니다 StackOverflow