0

If I have object with following structure:

var test = {
     property1: "value1",
     property2: "value2",
     property3: "value3",
     property4: "value4",
     property5: "value5"
}

Assuming that property names are fixed and not always in this order, what is the most elegant way to convert this object into following one:

var test_copy = {
     prop1Copy: "value1",
     propConcat: "value2, value3, value4, value5"
}
4
  • 1
    How is the name prop1Copy generated? And, how do you know what value it gets? Remember, most of the time properties do not have an order to them. Commented Aug 3, 2016 at 21:40
  • prop1Copy is always generated by conactenating values of property2, property3, property4 and property5 in that particular order Commented Aug 3, 2016 at 21:42
  • Properties don't generally have any order to them. I was asking how the actual property name `prop1Copy" is generated? Is that just a hardwired property name? Commented Aug 3, 2016 at 21:46
  • Are all your property names just hardwired to "property1", "property2", etc...? Or are you looking for a generic scheme that takes whatever properties are on an object and creates your copy using whatever properties are there? Commented Aug 3, 2016 at 21:48

4 Answers 4

2

I don't think there's any particularly elegant way to do this.

Since your input data has a small number fixed keys there's barely any point using a loop, so this works:

function munge(o) {
    return {
        prop1Copy: o.property1,
        propConcat: [o.property2, o.property3, o.property4, o.property5].join(', ')
    }
}
Sign up to request clarification or add additional context in comments.

2 Comments

Thanks! This was exactly what I was looking for. As long as keys are fixed and there are not to many of them this is the easiest way to concatenate values.
Assuming that you have only 5 properties.
0

Try this:

function concatObject(object, levels){
    var currentLevel = 0;
    var newObj = {propConcat: ""};
    for(var prop in object){
        if(currentLevel < levels){
            newObj[prop] = object[prop];
        }
        else{
            newObj["propConcat"] += object[prop];
        }
    }
}

concatObject(test, 1) would give you the answer, however it would keep the same property name for the variables. You need some kind of function of mapping if you want to change the actual property names (example: from property1 to prop1copy)

This would transform property# to property#copy:

function concatObject(object, levels){
    var currentLevel = 0;
    var newObj = {propConcat: ""};
    for(var prop in object){
        if(currentLevel < levels){
            newObj[prop+"copy"] = object[prop];
        }
        else{
            newObj["propConcat"] += object[prop];
        }
    }
}

Comments

0

Im not sure what you need to accomplish here. But if you want copy first item and concat all other take a look at this.

function concatValues (obj) {
    var resObj = {prop1Copy: ""}, count = 0, mergedArr = [];
    for (var k in obj) {
       count == 0 ? resObj.prop1Copy = obj[k] : mergedArr.push(obj[k]);
       count++;
    }
   resObj.propConcat = mergedArr.join(", ");
   return resObj;
}

Hope this helps

Comments

0

Here is a more generic solution that would work on a wider range of input with some caveats.

function concatenateObjectValues(obj) {
    //If you want the output to be sorted differently, you need to provide your own sort order. This sorts by alphabetical order
    var keys = Object.keys(test).sort();

    //assuming the first property would always be the copy
    //removing the first element and returning it
    var copyProp = keys.unshift();

    //generate an array that has the values of the remaining properties from the input
    var concatProp = keys.reduce(function(memo, key) {
        memo.push(test[key]);
        return memo;
    }, []);

    //create `propConcat` and combine the values using the specified separator
    var newObj = {
        propConcat: concatProp.join(", ")
    };

    //add the `prop1Copy` property. The first part of the name would be derived from the actual first property .
    newObj[copyProp + "Copy"] = obj[copyProp];

    return newObj;
}
  • Assuming you want your concatenated properties in alphabetical order, the above would work. If not, then you would need to specify a different sort order. This can be passed in as an argument, if it's going to vary).
  • if the copy property is going to vary, then this code might also need to change. Also, something that can be passed in as a parameter - trivial if it's just the index, but if you have to look them up by name (e.g., if you want to say "prop1" regardless of where it is., you need to also implement that).
  • if the names propConcat and prop1Copy need to vary more than that, the logic needs to be implemented. Or the values passed in...
  • there is no validation. I kept it simple for the sake of the example, but some error handling would be good.

To be honest, if your expected output is going to vary by more than one thing, for example, if you need the copy property to be different and the sort order to be different, then it might just be better to scrap this function. Big variations in the expected input/output make it a bit unwieldy, if you need to pass in most of the stuff to construct the result.

Comments

Your Answer

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

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.