admin管理员组

文章数量:1279237

I have a series of editable lists which, on a press of a button should be transformed into some sort of data structure. When it has been turned into some sort of data I need to add duplicates together.

Example:

  • 200g banana
  • 100g apple
  • 200g apple

Should be turned into a data list of some sort and should in the end look like this:

  • 200g banana
  • 300g apple

Here's my attempt:

//button click event
$(".calculate").bind("click", function(e)
{
    //get the correct parent of the button
    var parent = $(this).closest("#calc");

    //get relevant data
    parent.find(".options").each(function(index, element)
    {
        var opt1 = $(this).children(".opt1").children("input").val(); //weight
        var opt2 = $(this).children(".opt2").children("input").val(); //ingredient
    });
});

Basically I click the button and the above script finds all the relevant data.

How can I turn this into a multidimensional array or a list of objects I can search for duplicates in?

When I try to make a dynamic object it seems to fail and when I make a multidimensional array to search in I get blocked by inArray's inability to search through them.

Problem recap: I am able to get the user data no problem. Turning it into a list and adding together duplicates is the problem.

I have a series of editable lists which, on a press of a button should be transformed into some sort of data structure. When it has been turned into some sort of data I need to add duplicates together.

Example:

  • 200g banana
  • 100g apple
  • 200g apple

Should be turned into a data list of some sort and should in the end look like this:

  • 200g banana
  • 300g apple

Here's my attempt:

//button click event
$(".calculate").bind("click", function(e)
{
    //get the correct parent of the button
    var parent = $(this).closest("#calc");

    //get relevant data
    parent.find(".options").each(function(index, element)
    {
        var opt1 = $(this).children(".opt1").children("input").val(); //weight
        var opt2 = $(this).children(".opt2").children("input").val(); //ingredient
    });
});

Basically I click the button and the above script finds all the relevant data.

How can I turn this into a multidimensional array or a list of objects I can search for duplicates in?

When I try to make a dynamic object it seems to fail and when I make a multidimensional array to search in I get blocked by inArray's inability to search through them.

Problem recap: I am able to get the user data no problem. Turning it into a list and adding together duplicates is the problem.

Share Improve this question edited Sep 11, 2015 at 18:05 Michael B. Currie 14.7k10 gold badges46 silver badges61 bronze badges asked Jul 17, 2012 at 12:47 EirinnEirinn 8361 gold badge10 silver badges23 bronze badges 5
  • Could you put it on JSFiddle for us? – Some Guy Commented Jul 17, 2012 at 12:50
  • Can you show a sample of your html too, so we can get a better idea of what's going on. Preferably, put together a simple jsfiddle to illustrate the problem. – Jamiec Commented Jul 17, 2012 at 12:51
  • The closest("#calc"); implies duplicate IDs used, say its not true. – Mark Schultheiss Commented Jul 17, 2012 at 13:37
  • Don't worry Mark, it is only there until I clean up the code and add a class instead. – Eirinn Commented Jul 17, 2012 at 13:48
  • +1'ed just for the Carly Rae Jepsen reference. – JoshMock Commented Jul 17, 2012 at 18:04
Add a ment  | 

3 Answers 3

Reset to default 8

I will suggest you to have a global object that will contain the summary, this will look like this:

$(".calculate").bind("click", function(e)
{
    var fruits = {};

    //get the correct parent of the button
    var parent = $(this).closest("#calc");

    //get relevant data
    parent.find(".options").each(function(index, element)
    {
        var opt1 = $(this).children(".opt1").children("input").val(); //weight
        var opt2 = $(this).children(".opt2").children("input").val(); //ingredient

        // here is my code
        if(fruits[opt2] == undefined) {
            fruits[opt2] = opt1;
        } else {
            // assuming that opt1 is an integer
            fruits[opt2] += opt1;
        }
    });

    // use fruits variable here
});

Here's another variant, which also does some simple parsing in case you have 100g as input, versus 100. Also, the data structure gets reinitialized every time, so everything does not get doubled on every click.

$(".calculate").bind("click", function(e)
{
    //get the correct parent of the button
    var parent = $(this).closest("#calc");

    var ingredients = {};

    var extractWeight = function (input) {
        // you can add other logic here
        // to parse stuff like "1kg" or "3mg"

        // this assumes that everything is
        // in grams and returns just the numeric
        // value
        return parseInt(input.substring(0, input.length - 1));
    }

    //get relevant data
    parent.find(".options").each(function(index, element)
    {
        var opt1 = $(this).children(".opt1").children("input").val(); //weight
        var opt2 = $(this).children(".opt2").children("input").val(); //ingredient

        // initialize to 0 if not already initialized
        ingredients[opt2] = ingredients[opt2] ? ingredients[opt2] : 0;
        ingredients[opt2] += extractWeight(opt1);
    });
});​

Here are some tips:

  • {} is called an object literal and is used to create a new empty object
  • object members can be accessed dynamically through the [] notation (i.e. if x === "name" then o[x] === o.name)
  • variables are visible inside functions that are at the same level or deeper in the scope - like in my example I use ingredients in the each function.
  • arrays in JavaScript only support numeric keys, so you won't have stuff like PHP's "associative arrays". Objects fill this gap in JS.

Here is a jsFiddle that does what you're looking for :) http://jsfiddle/LD9TY/

It has two inputs, one for the item name and the other for the amount. When you click add, it checks an object to see if the item was already added. If so, it increments the amount for that item based on your input. If not, it adds that item with the amount you specified. It then goes and builds a ul with all the items in your "store".

Note that this is a quick and dirty example, so there is no type checking or validation going on :)

本文标签: javascriptjQuery list of dataStack Overflow