'How to pass an object property as a parameter? (JavaScript)

I'm not sure if the title is appropriate for what I am trying to achieve

I am mapping JSON results to an array. Because I need to do this over and over again I would like to put the code into one function.

In the following examples I am repeating myself. I have properties called item.data1, item.data2 and in the second example item.something1, item.something2 ... How can I pass those properties as "general" arguments to the newly created function in order to use them there and not repeat myself to return those maps? The new function should be useable for the two examples below as well as for other cases where the properties could have different names.

service.getData(function(data) {
    var map = {};
    map = $.map(data, function(item, i) {
        var entry = {};

        entry.key = item.data1;
        entry.value = item.data2;

        return entry;
    });
});

service.getSomething(function(data) {
    var map = {};
    map = $.map(data, function(item, i) {
        var entry = {};

        entry.key = item.something1;
        entry.value = item.something2;

        return entry;
    });
});


Solution 1:[1]

this can be done using the [] operators instead of the .-notation just like in this fiddle ive created just for you :D:

    var data = [{
        data1: 'foo',
        data2: 'bar',
        something1: 'sparky',
        something2: 'arf arf!'},
    {
        data1: 'My name is',
        data2: 'What?',
        something1: 'my name is',
        something2: 'Who?!'}
    ];

    function test(data, prop) {
        var d_length = data.length;
        for (var i = 0; i < d_length; i++) {
            alert(data[i][prop]);
        }
    }

    test(data, 'data1');

Solution 2:[2]

You will need to pass the item object and a map of item-keys to entry-keys. This could either be two arrays, an array of tuples or something, or an object. Most simple method I could think of is to change the descriptor object into the entry itself:

function mapPropertyNames(source, dest) {
    for (var prop in dest)
        dest[prop] = source[dest[prop]];
    return dest;
}

// and use it like this:

var map = $.map(data, function(item, i) {
    return mapPropertyNames(item, {key:"something1", value:"something2"});
});

Solution 3:[3]

Something like

service.getData(function(data) {
    var map = {};
    var varNamePrefix = 'data';
    map = $.map(data, function(item, i) {
        return getProperties(item, varNamePrefix);
    });
});

service.getSomething(function(data) {
    var map = {};
    var varNamePrefix = 'something';
    map = $.map(data, function(item, i) {
        return getProperties(item, varNamePrefix);
    });
});

function getProperties(item, varNamePrefix) {
    var ret = {};
    ret.key = item[varNamePrefix + '1'];
    ret.value = item[varNamePrefix + '2'];
    return ret;
}

May help?

Basically, you could use a function that takes a property prefix and uses it to form the actual property names to get from items.

Solution 4:[4]

A terrible solution... but it's in-line, therefore a superior solution.

copy(
  obj.loadimage.background,
  ...(()=>{let o={
    sx:0, sy:0, sw:32, sh:32, dx:50, dy:50, dw:32, dh:32
  }; return[o.sx, o.sy, o.sw, o.sh, o.dx, o.dy, o.dw, o.dh]})()
)

This is a "copy" function in p5js. It asks for a source image that it will crop from, then a series of numbers...

  • [sx & xy]: starting x/y to crop with on source image.
  • [sw & sh]: starting width and height to crop with on source image.
  • [dx & dy]: destination x/y to paste the cropped image.
  • [dw & dh]: destination width and height to paste the cropped image.

obviously a declared object prior to the function would be cleaner and preferred... but this is an in-line solution, which is always top-notch.

- Take an arrow function ()=>{}
- Stuff an object in it ()=>{let o={key:val}}
- Return your object in an ordered array ()=>{let o={key:val};return[o.key,]}
- Auto-run your func (()=>{let o={key:val};return[o.key,]})()
- Spread operator on it ...(()=>{let o={key:val};return[o.key,]})()

And you're done! The spread operator will separate out your labeled numbers in the proper order and the function will be happy and none the wiser!

Or you could do it the boring way.

let o={key:val,key:val,}
copy(img, ...[o.key,o.key,])

Solution 5:[5]

try this:

service.getData(function(data, props) {// props is a property object
    var map = {};
    map = $.map(data, function(item, i) {
        var entry = {};

        for (var key in props) {
            entry[key] = item[key]
        }

        return entry;
    });
});

or use a property array

service.getData(function(data, props) {// props is like ['data1', 'data2']
    var map = {};
    map = $.map(data, function(item, i) {
        var entry = {};

        for (var j = 0, k = props.length; j < k; j++) {
            entry[props[j]] = item[props[j]]
        }

        return entry;
    });
});

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1 nozzleman
Solution 2 Bergi
Solution 3 Raibaz
Solution 4 Fox
Solution 5