4
\$\begingroup\$

Is it good to empty an array on focusout?

var arr = [];
$("#automobil").focus(function() {
    $.getJSON("auto.json", function(data) {
        $.each(data, function(key, value) {
            if ($.inArray(value.name, arr) === -1) {
                arr.push(value.name)
            }
        })
    });
}).autocomplete({
    source: function (request, response) {
        var term = $.ui.autocomplete.escapeRegex(request.term)
            , startsWithMatcher = new RegExp("^" + term, "i")
            , startsWith = $.grep(arr, function(value) {
                return startsWithMatcher.test(value.label || value.value || value);
            })
            , containsMatcher = new RegExp(term, "i")
            , contains = $.grep(arr, function (value) {
                return $.inArray(value, startsWith) < 0 &&
                    containsMatcher.test(value.label || value.value || value);
            });

        response(startsWith.concat(contains));
    }
}).focusout(function() {
    arr = [];
});    

In this case, auto.json isn't big, so arr[] isn't big either. But, in "real world examples", there can be large amounts of data, so the array needs to be empty on focusout (after the job is done), because of resources.

\$\endgroup\$
2
  • \$\begingroup\$ We need more context about what you try to do, what expect, what you get. \$\endgroup\$
    – vmariano
    Mar 27, 2015 at 12:45
  • 1
    \$\begingroup\$ if the array is in a function it is probably not needed unless there is significantly more code running after you are done with the array. If declared in a global context then arr=null; is a good practice. \$\endgroup\$ Mar 27, 2015 at 20:00

1 Answer 1

4
\$\begingroup\$

I believe this is a case of being too paranoid in optimization. Here's some problems:

  • Your arr is global. You should probably place this somewhere only the widget knows about.

  • You're clearning the array... by creating another array. You're spawning more objects (in this case, an array) instead of cleaning up. The proper way to clear an array is to set length to 0. If nothing references the items in the array, they'll get GC'ed eventually.

  • autocomplete, focus, and focusout can go out of sync. When you focus on the input, you do getJSON. However, your autocomplete will run regardless if the request has returned. So that means the array might be empty when autocomplete runs. When you focus out, you cleared your array, so if you focus in again, this happens.

  • You're making unnecessary AJAX calls. On focus, you're calling AJAX. In the real world, waiting for AJAX is a more painful experience than memory consumption. With proper practice, the GC can and will reclaim memory but you can't reclaim the time you waited for AJAX.

I suggest you do the following instead:

  • You can limit the returned results to a reasonable length. That way, even if you hit the server with AJAX for each keypress, the return won't take that long.

  • Cache your results. Have some internal logic which caches returned data into an array (add when non-existent, update if existing). The problem here isn't the size of your cached data. It's the way you're discarding data and retrieving them back again.

\$\endgroup\$
1
  • \$\begingroup\$ I tried to put arr inside of source function, but it didn't work. Also, I don't know how to do it without AJAX (in this particular case). Also, I know nothing about how to Cache results, maybe it has something to do with server-side (for example PHP), but I'm still on client side, I'm learning only client side for now (JavaScript, jQuery... ). Anyway, thank you for this answer! \$\endgroup\$
    – PeraMika
    Mar 29, 2015 at 14:56

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.