This is how I get the data:
const dataSaved = [{
count: 52,
deliveryAmount: 0,
discountAmount: 7,
guests: 2,
refundedAmount: 9,
serviceChargeAmount: 4,
storeId: "aslkasad",
subtotal: 2,
taxAmount: 4,
total: 3
}, {
count: 52,
deliveryAmount: 0,
discountAmount: 7,
guests: 2,
refundedAmount: 9,
serviceChargeAmount: 4,
storeId: "ldfgfgdf",
subtotal: 2,
taxAmount: 4,
total: 3
}]
So basically I have made a method in which I'm filtering an array of objects and just taking out the fields I need:
getDataParsed(dataSaved, storeFieldRequired) {
const barData = [];
for (const store of dataSaved) {
barData.push({
data: [store.storeFieldRequired],
label: store.storeId
});
}
return barData;
}
When I want to get an specific field of the array, my [store.storeFieldRequired] brings undefined.
How can I solve it?
Instead of using store.storeFieldRequired, it is needed to use store[storeFieldRequired]. They have different meanings.
store.storeFieldRequired means to get the value of storeFieldRequired key on store object.
store[storeFieldRequired] means to get the value of storeFieldRequired variable value key on store object.
const dataSaved = [{
count: 52,
deliveryAmount: 0,
discountAmount: 7,
guests: 2,
refundedAmount: 9,
serviceChargeAmount: 4,
storeId: "aslkasad",
subtotal: 2,
taxAmount: 4,
total: 3
}, {
count: 52,
deliveryAmount: 0,
discountAmount: 7,
guests: 2,
refundedAmount: 9,
serviceChargeAmount: 4,
storeId: "ldfgfgdf",
subtotal: 2,
taxAmount: 4,
total: 3
}];
function getDataParsed(dataSaved, storeFieldRequired) {
const barData = [];
for (const store of dataSaved) {
barData.push({
data: [store[storeFieldRequired]],
label: store.storeId
});
}
return barData;
}
console.log(getDataParsed(dataSaved, 'count'));
Simply, using Array.prototype.map, you can get the result.
const dataSaved = [{
count: 52,
deliveryAmount: 0,
discountAmount: 7,
guests: 2,
refundedAmount: 9,
serviceChargeAmount: 4,
storeId: "aslkasad",
subtotal: 2,
taxAmount: 4,
total: 3
}, {
count: 52,
deliveryAmount: 0,
discountAmount: 7,
guests: 2,
refundedAmount: 9,
serviceChargeAmount: 4,
storeId: "ldfgfgdf",
subtotal: 2,
taxAmount: 4,
total: 3
}];
function getDataParsed(dataSaved, storeFieldRequired) {
return dataSaved.map((item) => ({
data: [item[storeFieldRequired]],
label: item.storeId
}));
}
console.log(getDataParsed(dataSaved, 'count'));
Access the variable with bracket-[] notation. Example => data: [store[storeFieldRequired]].
getDataParsed(storeData, storeFieldRequired) {
const barData = [];
for (const store of storeData) {
barData.push({
data: [store[storeFieldRequired]], // change this line from data: [store.storeFieldRequired] to data: [store[storeFieldRequired]]
label: store.storeId
});
}
return barData;
}
Related
I have to create an array of arrays based on some object attributes.
So my object looks like this:
const data = {
projectId: 5,
userIds: [2, 3, 1, 5],
dateIds: [99, 100, 101, 102, 103],
task: 'task',
duration: 8,
description: 'description'
}
Based on the userIds and dateIds I have to create an array of arrays with every attribute like this:
[[projectId, userId, dateId, task, duration, description]] <- this is what every number means
For every userId and dateId i have to create a new array.
And based on my example should be like this:
[[5, 2, 99, 'task', 8, 'description'],
[5, 3, 99 , 'task', 8, 'description'],
[5, 1, 99, 'task', 8, 'description'],
[5, 5, 99, 'task', 8, 'description'],
[5, 2, 100, 'task', 8, 'description'],
[5, 3, 100, 'task', 8, 'description']
... etc]]
Hope i explained my issue well. Thank you for your time!
My function:
const data = { projectId: 5, userIds: [2, 3, 1, 5], date: [99, 100, 101, 102], task: 'task', duration: 'duration', description: 'description' }
const parentArray = []
data.date.map(object =>
data.userIds.map(anotherObject => {
// console.log(anotherObject, object)
parentArray.push([data.projectId, object, anotherObject, data.task, data.duration, data.description])
}
))
console.log(parentArray)
const data = {
projectId: 5,
userIds: [2, 3, 1, 5],
dateIds: [99, 100, 101, 102, 103],
task: 'task',
duration: 8,
description: 'description'
}
const result = data.userIds.map(uid => {
return data.dateIds.map(did => [data.projectId, uid, did, data.task, data.duration, data.description])
}).flat();
console.log(result);
Not exactly what you asked for but using your example you can create an array of objects which might add clarity by naming the properties (if some other user needs something like this). Note how I pass in the data and reference it with this and loop through the dateId's. Key is I never have to reference the original array, perhaps making this more maintainable internally;
const data = {
projectId: 5,
userIds: [2, 3, 1, 5],
dateIds: [99, 100, 101, 102, 103],
task: 'task',
duration: 8,
description: 'description'
};
let x = [];
data.userIds.forEach(function(userid, index) {
this.dateIds.map((dateid, idx) => {
x.push({
project: this.projectId,
user: userid,
dateid: dateid,
tsk: this.task,
dur: this.duration,
desc: this.description
});
});
}, data);
x.forEach(function(el, index, array) {
console.log(el);
});
Working with an array of objects like:
[
{
orderItemId: 180,
product_id: 1,
product_quantity: 3,
product_price: 18,
product_name: 'American BBQ DOG',
extra_id: 1,
extra_quantity: 3,
extra_price: 2,
extra_name: 'Mustard (60 g)',
},
{
orderItemId: 180,
product_id: 1,
product_quantity: 3,
product_price: 18,
product_name: 'American BBQ DOG',
extra_id: 3,
extra_quantity: 3,
extra_price: 2,
extra_name: 'Roasted onions (30 g)',
}
]
I am trying to reduce the array on matching values for the orderItemId key and achieve an desired output like:
const desired = [
{
orderItemId: 180,
product_id: 1,
product_quantity: 3,
product_price: 18,
product_name: 'American BBQ DOG',
extra: [
{
extra_id: 1,
extra_quantity: 3,
extra_price: 2,
extra_name: 'Mustard (60 g)',
},
{
extra_id: 3,
extra_quantity: 3,
extra_price: 2,
extra_name: 'Roasted onions (30 g)',
}
]
}
];
Any ideas? I tried several logic but failed.
Here's one way to do it. It just uses Array.find() to find a previous item with the same orderItemId, if found, appends the extras to its extra array. If the original array is very large, consider using an object or a Map as the accumulator passed to the .reduce call and using Object.values() later.
If you need to handle extra logic such as adding product_quantity or deduplicating extra, you'll need to handle that as well.
const arr = [
{
orderItemId: 180,
product_id: 1,
product_quantity: 3,
product_price: 18,
product_name: "American BBQ DOG",
extra_id: 1,
extra_quantity: 3,
extra_price: 2,
extra_name: "Mustard (60 g)",
},
{
orderItemId: 180,
product_id: 1,
product_quantity: 3,
product_price: 18,
product_name: "American BBQ DOG",
extra_id: 3,
extra_quantity: 3,
extra_price: 2,
extra_name: "Roasted onions (30 g)",
},
];
const reduced = arr.reduce((acc, val) => {
const {
extra_id,
extra_quantity,
extra_price,
extra_name,
...otherFields
} = val;
const existing = acc.find((item) => item.orderItemId === val.orderItemId);
if (!existing) {
acc.push({
...otherFields,
extra: [
{
extra_id,
extra_quantity,
extra_price,
extra_name,
},
],
});
return acc;
}
existing.extra.push({ extra_id, extra_quantity, extra_price, extra_name });
return acc;
}, []);
console.log(reduced);
Edit: Here's a version that uses an object as a lookup so it doesn't have to go through the entire accumulated array each time. The acc (accumulator) object is basically just an object where the property keys are the orderItemId and the value is the new merged object with that key.
const arr = [
{
orderItemId: 180,
product_id: 1,
product_quantity: 3,
product_price: 18,
product_name: "American BBQ DOG",
extra_id: 1,
extra_quantity: 3,
extra_price: 2,
extra_name: "Mustard (60 g)",
},
{
orderItemId: 180,
product_id: 1,
product_quantity: 3,
product_price: 18,
product_name: "American BBQ DOG",
extra_id: 3,
extra_quantity: 3,
extra_price: 2,
extra_name: "Roasted onions (30 g)",
},
];
const reducedObject = arr.reduce((acc, val) => {
const {
extra_id,
extra_quantity,
extra_price,
extra_name,
...otherFields
} = val;
const existing = acc[val.orderItemId];
if (!existing) {
acc[val.orderItemId] = {
...otherFields,
extra: [
{
extra_id,
extra_quantity,
extra_price,
extra_name,
},
],
};
return acc;
}
existing.extra.push({ extra_id, extra_quantity, extra_price, extra_name });
return acc;
}, {});
const reduced = Object.values(reducedObject);
console.log(reduced);
With this approach you can use it with different data structure also, whitout declare fields names (or key names).
In practice comparison and aggregation.
var alist=[
{
orderItemId: 180,
product_id: 1,
product_quantity: 3,
product_price: 18,
product_name: 'American BBQ DOG',
extra_id: 1,
extra_quantity: 3,
extra_price: 2,
extra_name: 'Mustard (60 g)',
},
{
orderItemId: 180,
product_id: 1,
product_quantity: 3,
product_price: 18,
product_name: 'American BBQ DOG',
extra_id: 3,
extra_quantity: 3,
extra_price: 2,
extra_name: 'Roasted onions (30 g)',
}
];
function jS(o){
return JSON.stringify(o);
}
function equals(a,b){
var aa = jS(a);
var bb = jS(b);
return aa == bb;
}
function hLen(o){
return Object.keys(o).length;
}
function hKeys(h){
return Object.keys(h);
}
function reduce(arr){
var ha=arr[0];
var hb=arr[1];
var hc={};
var xc1={}; //extra 1 when are different
var xc2={}; //extra 2 when are different
maxhlen = Math.max(hLen(ha),hLen(hb));
akeys = hKeys(ha);
bkeys = hKeys(hb);
for(i=0;i<maxhlen;i++){
k=akeys[i];
if (ha[k]==hb[k]){
hc[k]=ha[k];
}else{
xc1[k]=ha[k];
xc2[k]=hb[k];
}
}
hc["extra"]=[xc1,xc2];
return hc;
}
res=reduce(alist);
console.log(res);
I have the following code:
conditions.slice(0).filter(condition => condition.processsteptemplate === stepId);
It should slice some objects out of an array. Problem is that the === does not match so all elements are still in the array ...
whats my fail
UPDATE:
Sample Code:
var conditions = [{
id: 14,
conditiontype: 1,
processsteptemplate: 9,
deleted: false,
processTemplate_id: 0
},
{
id: 15,
conditiontype: 1,
processsteptemplate: 9,
deleted: false,
processTemplate_id: 0
},
{
id: 16,
conditiontype: 1,
processsteptemplate: 10,
deleted: false,
processTemplate_id: 0
}
],
stepId = 9;
const output = conditions.slice(0).filter(condition => condition.processsteptemplate === stepId);
console.log(output)
here the array with processsteptemplate = 10 is removed
let arr = [
{id: 14, conditiontype: 1, processsteptemplate: 9, deleted: false, processTemplate_id: 0},
{id: 15, conditiontype: 1, processsteptemplate: 9, deleted: false, processTemplate_id: 0},
{id: 16, conditiontype: 1, processsteptemplate: 10, deleted: false, processTemplate_id: 0}
]
let step = 9;
let result = arr.filter((e) => e.processsteptemplate === step);
console.log(result);
What you were probably doing wrong was that you were assuming
arr.filter((e) => e.processsteptemplate === step);
would change the value in the current array, that is not true, it would return a new array which is now stored in result as you can now see in the above code snippet
This is a SCHOOL PROJECT and not something being used on a functioning website, so no worries that it's client side only! We've been asked to expand upon our last assignment to create a script that would allow out teacher to input an ARTIST name in the search box on our "music store" homepage, which would then search the JavaScript array that we built and then return the results in a new window with the "Album Name", as well as a link to another page for additional information (not so much worried about that link just yet, trying to get the actual search & album return functionality working first!).
Below is what I have, and the JS FIddle is: http://jsfiddle.net/2AS53/. Any assistance or ideas on what's wrong would be greatly appreciated. Thanks for your help...
<div class="form">
<form method="get" action="input">
<input name="textfield" type="text" class="colortext" placeholder=" Search entire store..." />
</form>
Search
< script >
var myInventory = [{
id: 001,
title: "Total Life Forever",
artist: "FOALS",
price: 14.99,
released: "March, 2009",
tracks: [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12],
quantity: 1
}, {
id: 002,
title: "Bein Love",
artist: "Locksley",
price: 14.99,
released: "April, 2012",
tracks: [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12],
quantity: 1
}, {
id: 003,
title: "Privileged",
artist: "Nick Moss",
price: 14.99,
released: "June, 2011",
tracks: [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12],
quantity: 1
}, {
id: 004,
title: "Asondeguerra",
artist: "Juan Louis Guerra",
price: 14.99,
released: "September, 2013",
tracks: [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12],
quantity: 1
}, {
id: 017,
title: "Way Out Here",
artist: "Josh Thompson",
price: 14.99,
released: "August, 2010",
tracks: [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12],
quantity: 1
}, {
id: 018,
title: "Tremolo",
artist: "The Pines",
price: 14.99,
released: "January, 2007",
tracks: [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12],
quantity: 1
}, {
id: 019,
title: "Live From Freedom Hall",
artist: "Lynyrd Skynyrd",
price: 14.99,
released: "June, 2010",
tracks: [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12],
quantity: 1
}, {
id: 020,
title: "Achin & Shakin",
artist: "Laura Bell Bundy",
price: 14.99,
released: "July, 2013",
tracks: [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12],
quantity: 1
}, {
id: 021,
title: "Here I Am",
artist: "Marvin Sapp",
price: 14.99,
released: "November, 2011",
tracks: [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12],
quantity: 1
}, {
id: 022,
title: "Just James",
artist: "J Moss",
price: 14.99,
released: "March, 2011",
tracks: [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12],
quantity: 1
}, {
id: 013,
title: "Tom Petty - Live",
artist: "Tom Petty",
price: 14.99,
released: "May, 2010",
tracks: [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12],
quantity: 1
}, ];
search.onclick = myInventory() {
var formInput = document.getElementById("formInput").value;
for (i = 0; i < data.length; i++) {
if (data[i] == formInput) {
onclick = "java script: openWin('search.html') {"Album Name:"' title};
} else {
onclick = "java script: openWin('search.html') ("No Artists Found");
}
}
}; </script>
You had some typos, that's why I've created a working jsFiddle: http://jsfiddle.net/2AS53/3/
And here are main things, which prevent your code from working.
You don't have to add <script> tags in the JSFiddle script frame. Only pure JavaScript goes there. That;s why you have Uncaught SyntaxError: Unexpected token < in error console.
In myInventory() method you're referring to data variable, but you don't have such variable, you have variable var myInventory = [.... And this is another error. You define variable and then function with the same name. Second declaration will override first one.
JSFiddle web site places your JS code inside listener for window.load event, so, your data and onclick event handler are not defined in a global scope but in scope of window.load event listener. That's why there is a 'Uncaught ReferenceError: myInventory is not defined' error in error console. You can see yourself whan exactly jsfiddle produces, when right click in a result frame and choose 'View frame source'.
Since everything is inside window.load event handler, in order to attach event listener to search button, you should first get your button element (I've used document.getElementById) and then either do
document.getElementById('searchBtn').onclick = function() {
}
or
document.getElementById('searchBtn').addEventListener('click', function() {
});
Second way is more flexible, since it allows you to have multiple event listeners for a single event. I've added id="searchBtn" to search button in HTML.
use onClick function in your HTML code and try
I've looked at this Stack question, "Removing duplicate objects with Underscore for Javascript" and that is exactly what I am trying to do, but none of the examples work. In fact I can not get any iterator function to work with _.uniq.
_.uniq([1, 2, 1, 3, 1, 4]);
> [1, 2, 3, 4]
_.uniq([1, 2, 1, 3, 1, 4], false, function(a){ return a===4;});
> [1, 2, 3, 4]
_.uniq([1, 2, 1, 3, 1, 4], true, function(a){ return a===4;});
> [1, 2, 1, 3, 1, 4]
_.uniq([1, 2, 1, 3, 1, 4], false, function(a){ return false;});
> [1, 2, 3, 4]
_.uniq([1, 2, 1, 3, 1, 4], false, function(a){ return true;});
> [1, 2, 3, 4]
var people = [ { name: 'John', age: 20 }, { name: 'Mary', age: 31 }, { name: 'Kevin', age: 20 }];
_.uniq(people, false, function(p){ return p.age; });
> [ { age: 20, name: "John" },
{ age: 31, name: "Mary" },
{ age: 20, name: "Kevin" } ]
I would do:
_.uniq(_.map(people, function(p){ return p.age; }));
> [20, 31]
but it returns only the mapped value, not the original object.
Any help appreciated. I am using underscore version 1.1.7
I had the same problem. It is caused because _.uniq() returns a new reduced array so you have to assing it to a variable. So with this little correction it has to work.
var people = [ { name: 'John', age: 20 }, { name: 'Mary', age: 31 }, { name: 'Kevin', age: 20 }];
people = _.uniq(people, false, function(p){ return p.age; });
[ { age: 20, name: "John" },
{ age: 31, name: "Mary" } ]
Looks like comparison functions for _.uniq were introduced in 1.2.0
from the changelog:
_.uniq can now be passed an optional iterator, to determine by what criteria an object should be considered unique.