25

Consider such an object with a prototype chain:

var A = {};
var B = Object.create(A);
var C = Object.create(B);

How to check in runtime if C has A in its prototype chain?

instanceof doesn't fit as it's designed to work with constructor functions, which I'm not using here.

hippietrail
  • 15,848
  • 18
  • 99
  • 158
Kos
  • 70,399
  • 25
  • 169
  • 233

2 Answers2

22

My answer will be short…

You could use the isPrototypeOf method, which will be present in case your object inherits from the Object prototype, like your example.

example:

A.isPrototypeOf(C) // true
B.isPrototypeOf(C) // true
Array.prototype.isPrototypeOf(C) // false

More info can be read here: Mozilla Developer Network: isPrototypeOf

Couto
  • 843
  • 1
  • 6
  • 16
  • 1
    +1 Simple solution. Although your examples are completely correct, it would be `Array.prototype.isPrototypeOf(C)` to check whether `C` is an array (I found your last example a little bit ambiguous - using `isPrototypeOf` on a function is usually not what you want). – pimvdb Feb 06 '12 at 15:51
  • You're absolutely right, i didn't want to lose too much time since an answer was already given at the time, so i didn't think too much on the examples, my objective was only to show the method available... still i will correct the example given with your answer, since as you said and i agree, my last example is ambiguous, thanks for the notice =) – Couto Feb 06 '12 at 21:47
  • Just a quick question: how is it possible for object not to inherit from Object? Any object has a [[Prototype]] reference that through chain of prototypes eventually leads to Object.prototype. – Viktor Stolbin Nov 08 '15 at 13:27
  • @ViktorStolbin You can use `var a = Object.create(null);` To get an object with null as prototype. – Couto Feb 09 '16 at 13:11
4

You could iterate back through the prototype chain by calling Object.getPrototypeOf recursively: http://jsfiddle.net/Xdze8/.

function isInPrototypeChain(topMost, itemToSearchFor) {
    var p = topMost;

    do {

        if(p === itemToSearchFor) {
            return true;
        }

        p = Object.getPrototypeOf(p); // prototype of current

    } while(p); // while not null (after last chain)

    return false; // only get here if the `if` clause was never passed, so not found in chain
}
pimvdb
  • 151,816
  • 78
  • 307
  • 352
  • +1 Was about to post a near *identical* answer, even with the `do-while`, which I don't see too often. But yours is made into a function, which is nicer. – RightSaidFred Dec 09 '11 at 17:34
  • @RightSaidFred: Funny, I was also thinking about the fact that I was using the `do` keyword which I almost never do. – pimvdb Dec 09 '11 at 17:37
  • I'm surprised that there isn't an `Object.hasPrototype` proposal for ES6 that does exactly what your function does. It just seems a natural complement `Object.create` as `instanceof` is to `new Constructor`. It could even accept a function as the second argument, which would use the function's `prototype` as the target. – RightSaidFred Dec 09 '11 at 17:44
  • Can you confirm that recent EcmaScript didn't add a built-in feature for that? I have a memory that this existed, but might be just my imagination :-) – Kos Dec 13 '11 at 17:20
  • @Kos: I don't know which function that should be. None of the functions listed at MDN seem to implement this: https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Object#Methods. – pimvdb Dec 13 '11 at 17:39