function sortedIndex(array, value, callback, thisArg) {
    if (!array) {
      return 0;
    }
    var mid,
        low = 0,
        high = array.length;

    if (callback) {
      if (thisArg) {
        callback = bind(callback, thisArg);
      }
      value = callback(value);
      while (low < high) {
        mid = (low + high) >>> 1;
        callback(array[mid]) < value ? low = mid + 1 : high = mid;
      }
    } else {
      while (low < high) {
        mid = (low + high) >>> 1;
        array[mid] < value ? low = mid + 1 : high = mid;
      }
    }
    return low;
  }
Uses a binary search to determine the smallest index at which the `value`
should be inserted into `array` in order to maintain the sort order of the
sorted `array`. If `callback` is passed, it will be executed for `value` and
each element in `array` to compute their sort ranking. The `callback` is
bound to `thisArg` and invoked with 1 argument; (value).

@static
@memberOf _
@category Arrays
@param {Array} array The array to iterate over.
@param {Mixed} value The value to evaluate.
@param {Function} [callback=identity] The function called per iteration.
@param {Mixed} [thisArg] The `this` binding for the callback.
@returns {Number} Returns the index at which the value should be inserted
 into `array`.
@example

_.sortedIndex([20, 30, 40], 35);
// => 2

var dict = {
  'wordToNumber': { 'twenty': 20, 'thirty': 30, 'thirty-five': 35, 'fourty': 40 }
};

_.sortedIndex(['twenty', 'thirty', 'fourty'], 'thirty-five', function(word) {
  return dict.wordToNumber[word];
});
// => 2

_.sortedIndex(['twenty', 'thirty', 'fourty'], 'thirty-five', function(word) {
  return this.wordToNumber[word];
}, dict);
// => 2