I managed to implement this way:
I need to get the hashcode from objects.
Object.prototype.GetHashCode = function () {
    var s = this instanceof Object ? stringify(this) : this.toString();
    var hash = 0;
    if (s.length === 0) return hash;
    for (var i = 0; i < s.length; ++i) {
        hash = ((hash << 5) - hash) + s.charCodeAt(i);
    }
    return hash;
};
Number.prototype.GetHashCode = function () { return this.valueOf(); };
As JSON.stringify will fail at circular references, I created another method to stringify it in a way I can get the most of an object as a string and compute the hashcode over it, as follows:
function isPlainObject(obj)
{
    if ((typeof (obj) !== "object" || obj.nodeType || (obj instanceof Window))
        || (obj.constructor && !({}).hasOwnProperty.call(obj.constructor.prototype, "isPrototypeOf"))
    )
    {
        return false;
    }
    return true;
}
function stringify(obj, s)
{
    s = s || "";
    for (var i in obj)
    {
        var o = obj[i];
        if (o && (o instanceof Array || isPlainObject(o)))
        {
            s += i + ":" + JSON.stringify(o);
        }
        else if (o && typeof o === "object")
        {
            s += i + ":" + "$ref#" + o;
        }
        else
        {
            s += i + ":" + o;
        }
    }
    return s;
}
There isn't much impact on performance. For large object it is the same and for small objects it loses, but is still pretty fast and safe. Performance test here.
Name                         op/s
---------------------------------
JSON.stringify large           62
stringify      large           62
JSON.stringify small    1,690,183
stringify      small    1,062,452
My GroupBy method
function GroupBy(a, keySelector, elementSelector, comparer)
{
    // set default values for opitinal parameters
    elementSelector = elementSelector || function(e) { return e; };
    comparer = comparer ||
        {
            Equals: function(a,b) { return a==b },
            GetHashCode: function(e) { return e.GetHashCode(); }
        };
    var key, hashKey, reHashKey;
    // keep groups separated by hash
    var hashs = {};
    for (var i = 0, n = a.length; i < n; ++i)
    {
        // in case of same hash, but Equals returns false
        reHashKey = undefined;
        // grabs the key
        key = keySelector(a[i]);
        // grabs the hashcode
        hashKey = comparer.GetHashCode(key);
        // if a hash exists in the list
        // compare values with Equals
        // in case it return false, generate a unique hash
        if (typeof hashs[hashKey] !== "undefined")
            reHashKey = comparer.Equals(key, hashs[hashKey].Key) ? hashKey : hashKey + " " + i;
        // if a new hash has been generated, update
        if (typeof reHashKey !== "undefined" && reHashKey !== hashKey)
            hashKey = reHashKey;
        // get/create a new group and add the current element to the list
        hashs[hashKey] = hashs[hashKey] || { Key: key, Elements: [] };
        hashs[hashKey].Elements.push(a[i]);
    }
    return hashs;
}
To test
var arrComplex =
[
    { N: { Value: 10 }, Name: "Foo" },
    { N: { Value: 10 }, Name: "Bar" },
    { N: { Value: 20 }, Name: "Foo" },
    { N: { Value: 20 }, Name: "Bar" }
];
//
var x = GroupBy(arrComplex
        , function(e) { return e.N; }
        , function(e) { return e.Name; }
        , {
              Equals: function(a,b) { return a.Value == b.Value },
              GetHashCode: function(e) { return e.GetHashCode(); }
          }
);
//
console.log(x);
Example on jsFiddle, now with Jedi.
But, accordingly to my tests, my implementation of GroupBy is slower than linq.js's GroupBy. It is only faster when I convert ToArray(). Maybe linq.js only really executes when I convert to array, that's why the difference, I am not sure on this part.
Test results
Name                         op/s
---------------------------------
GroupBy                   163,261
GroupByToArray            152,382
linq.js groupBy           243,547
linq.js groupBy toArray    26,309