2

I have a huge javascript object returned to a GET api call and i want to offer option to limit the number of keys returned like this:

GET /api/
{
   "bla1" : {
     ....
   },
   "bla2" : {
     ....
   },
   "bla3" : {
     ....
   },
   "bla4" : {
     ....
   },
   "bla5" : {
     ....
   },
   "bla6" : {
     ....
   },
   "bla7" : {
     ....
   }
}

when limit=2 is added to query params, this should be returned:

GET /api?limit=2
{
   "bla1" : {
     ....
   },
   "bla2" : {
     ....
   }
}

my main concern is response time. what if i have 100000 objects, i really don't want to loop over them. what shall i do?

EDIT: okey it doesn't have to be last. someone said it is arbitrary. so i guess it could be removed from any place.

Duaa Zahi
  • 357
  • 2
  • 9
  • 4
    How do you define "last"? Object keys are unordered. – Jonathan Hall Apr 03 '19 at 08:25
  • @Duaa Zahi, If it is ordered data, then I think you should not use `Objects`. Are you keys numeric? Do you want this in client or server side? When you say `limit=2`, that seems to be a server side solution. – Nishant Apr 03 '19 at 08:26
  • Which database are you using? – kemicofa ghost Apr 03 '19 at 08:26
  • 1
    Object property order is not guaranteed - so – Jack Bashford Apr 03 '19 at 08:27
  • @Flimzy technically... they are ordered, though I share your views and opinions, they are not 100% accurate. We should not really on the ordering though, so I wholeheartedly agree with the comment – Dellirium Apr 03 '19 at 08:27
  • This seems like a query string.. Are you trying to do that server-side? – wentjun Apr 03 '19 at 08:28
  • Have you considered forming an array using the keys of the object? – Jack Bashford Apr 03 '19 at 08:30
  • @Nishant they are not numeric. i just put this as example. this is sever side api. also i don't care about order, i just want the last x properties to be removed from the returned object – Duaa Zahi Apr 03 '19 at 08:30
  • 1
    @DuaaZahi how can it be "last" if you do not care about the order? – Dellirium Apr 03 '19 at 08:32
  • 1
    @Flimzy it is not arbitrary, there is a set of rules: http://www.ecma-international.org/ecma-262/6.0/#sec-ordinary-object-internal-methods-and-internal-slots-ownpropertykeys but I agree with you, just want to spread the information. I myself was not aware of this until recently – Dellirium Apr 03 '19 at 08:35
  • 2
    Wow nice XY problem here. Where is this object created in the first place? That's where you should implement this filter. – Kaiido Apr 03 '19 at 08:39
  • @Dellirium: This has changed, then. A JS object used to be defined as "an unordered collection of properties". See [here](https://stackoverflow.com/a/5525820/13860). I see as of ECMAScript 9, this is simply "A collection of properties". I'd say, relying on order is still fool-hardy. – Jonathan Hall Apr 03 '19 at 08:40
  • 1
    @Flimzy wholeheartedly agree. Just want to keep everyone informed, as this was brought up to me as well where I was still thinking about them like you did. – Dellirium Apr 03 '19 at 08:42

2 Answers2

1

There's really no way to accomplish your goal, without looping over at least part of your object. But you can limit your looping, by only looping over part of the object: Either the part you want to keep, or the part you want to discard.

It's easy to fetch N elements from any object, looping over only the keys to be kept:

let c = 0;
let target = {};
for (var property in object) {
  if (object.hasOwnProperty(property)) {
    target[property] = object[property];
    c++;
    if (c > N) {
        break;
    }
  }
}

You could also take the reverse approach, and delete N keys, looping over only the keys to be deleted:

let c = 0;
for (var property in object) {
  if (object.hasOwnProperty(property)) {
    delete object[property];
    c++;
    if (c > N) {
        break;
    }
  }
}
Jonathan Hall
  • 75,165
  • 16
  • 143
  • 189
1

How about:

 Object.entries(obj).slice(0, n).reduce(
     (acc, [k, v]) => (acc[k] = v, acc)
 );

Technically that's also a loop underneath, but over n elements selected upfront.

Mind you - the previous example is more memory efficient.

Michał Karpacki
  • 2,588
  • 21
  • 34