iwato Posted August 12, 2018 Share Posted August 12, 2018 (edited) BACKGROUND: I have created two functions of which the return value of one becomes the input value of the other. This other then returns a value that is the desire goal of the two functional procedures. So long as I run these functions separately, they produce the desired output. When I attempt to combine them, however, I inevitably fail. Please find below the successful procedure. I will not bother you with my unsuccessful attempts. INPUT ARRAY: var searchItems = [{category:'Search Podcast',count:'1',target:'キャップチブ'},{category:'Search Newsletter',count:'3',target:'proposition'},{category:'Search Podcast',count:'0',target:'Grammar Captive'},{category:'Search Podcast',count:'1',target:'proposition'},{category:'Search Podcast',count:'1',target:'文法'},{category:'Search Newsletter',count:'1',target:'Grammar Captive'},{category:'Search Podcast',count:'2',target:'proposition'},{category:'Search Podcast',count:'0',target:'Grammar Captive'},{category:'Search Podcast',count:'1',target:'proposition'},{category:'Search Podcast',count:'1',target:'文法'}]; The selectAndList( ) Function function selectAndList(propertyName, inputArr) { var propertyArr = []; inputArr.map(function(item) { propertyArr.push(item[propertyName]); }); return propertyArr; } The countOccurrence( ) Function function countOccurrence(inputArr) { var occurrenceArr = []; var copy = inputArr.slice(0); for (var i = 0; i < inputArr.length; i++) { var myCount = 0; for (var w = 0; w < copy.length; w++) { if (inputArr[i] == copy[w]) { myCount++; delete copy[w]; } } if (myCount > 0) { var a = new Object(); a.value = inputArr[i]; a.count = myCount; occurrenceArr.push(a); } } return occurrenceArr; }; Independent Calls Procedure: var selectedPropertyArr = selectAndList('target', searchItems); var occurrenceArr = countOccurrence(selectedPropertyArr); console.log(occurrenceArr); The result is an array with four objects each containing two properties (count and value) with their respective values. Indeed, it is the desired outcome. QUESTION: How to I combine the above two functions into a single function called countValueFrequency( ) with two arguments including propertyName and inputArr? OK. The following works, but is this the most efficient way of achieving the desired result? function countValueFrequency(propertyName, inputArr) { var propertyArr = []; inputArr.map(function(item) { propertyArr.push(item[propertyName]); }); function countOccurrence(inputArr) { var occurrenceArr = []; var copy = inputArr.slice(0); for (var i = 0; i < inputArr.length; i++) { var myCount = 0; for (var w = 0; w < copy.length; w++) { if (inputArr[i] == copy[w]) { myCount++; delete copy[w]; } } if (myCount > 0) { var a = new Object(); a.value = inputArr[i]; a.count = myCount; occurrenceArr.push(a); } } return occurrenceArr; }; return countOccurrence(propertyArr); } var newSelectedPropertyArr = countValueFrequency('target', searchItems); Roddy Edited August 12, 2018 by iwato Link to comment Share on other sites More sharing options...
~Code&Anime~ Posted August 12, 2018 Share Posted August 12, 2018 Your given code was quite hard to follow, I assume this code is supposed to count the number of property occurences of a given property for an array of objects? const countOccurences=(property, arr)=>{ let count=0 arr.map(item=>{ if(item.hasOwnProperty(property){ count++ } }) return count } 1 Link to comment Share on other sites More sharing options...
justsomeguy Posted August 13, 2018 Share Posted August 13, 2018 That function isn't recursive, so there's not really a reason to define a function inside another function and call it. You can just put the code inside the one function. Or, if you want to use the other function in other places, define it outside the function and just call it from inside. 1 Link to comment Share on other sites More sharing options...
iwato Posted August 13, 2018 Author Share Posted August 13, 2018 ~Code&Anime~: I am not familiar with your syntax, and it is therefore difficult for me to comment on it, but it does appear to oversimplify the task. Please correct me, if I am wrong. The countOccurrence() function receives as input an array that appears as something akin to the following: Array [ "キャップチブ", "proposition", "Grammar Captive", "proposition", "文法", "Grammar Captive", "proposition", "Grammar Captive", "proposition", "文法" ] The elements of this array are the values of a property called target found in each of the objects of the initial inputArr of the external function named countValueFrequency(). The countOccurrence() function counts the number of times that each of these values occurs in newly formed array and returns the result in the following format. Array [ Object, Object, Object, Object ] for which each object is of the following form: count: 1 value: "キャップチブ" count: 4 value: 'proposition' etc. Although somewhat awkward, these resulting objects must then be converted into arrays, so that they can be fed into the wordcloud2.js script for the creation of a word cloud. Roddy Link to comment Share on other sites More sharing options...
iwato Posted August 13, 2018 Author Share Posted August 13, 2018 JSG: Actually there is still another function that is included in the countValueFrequency() function that converts the objects of the resulting array of the countOccurrence() function into arrays. I just needed to know whether this is an acceptable procedure, and it appears that it is. Thank you. Roddy Link to comment Share on other sites More sharing options...
justsomeguy Posted August 13, 2018 Share Posted August 13, 2018 Well, it's not efficient to define a function inside another function that you're only going to use once, so if you're talking about efficiency then there's no reason to keep defining new functions every time you run that main function. Just put the code right in the one function. 1 Link to comment Share on other sites More sharing options...
iwato Posted August 15, 2018 Author Share Posted August 15, 2018 On 8/13/2018 at 2:39 PM, justsomeguy said: Well, it's not efficient to define a function inside another function that you're only going to use once, so if you're talking about efficiency then there's no reason to keep defining new functions every time you run that main function. Just put the code right in the one function. This makes good sense. Roddy Link to comment Share on other sites More sharing options...
~Code&Anime~ Posted August 15, 2018 Share Posted August 15, 2018 (edited) On 8/13/2018 at 9:02 PM, iwato said: ~Code&Anime~: I am not familiar with your syntax, and it is therefore difficult for me to comment on it, but it does appear to oversimplify the task. Please correct me, if I am wrong. The countOccurrence() function receives as input an array that appears as something akin to the following: Array [ "キャップチブ", "proposition", "Grammar Captive", "proposition", "文法", "Grammar Captive", "proposition", "Grammar Captive", "proposition", "文法" ] The elements of this array are the values of a property called target found in each of the objects of the initial inputArr of the external function named countValueFrequency(). The countOccurrence() function counts the number of times that each of these values occurs in newly formed array and returns the result in the following format. Array [ Object, Object, Object, Object ] for which each object is of the following form: count: 1 value: "キャップチブ" count: 4 value: 'proposition' etc. Although somewhat awkward, these resulting objects must then be converted into arrays, so that they can be fed into the wordcloud2.js script for the creation of a word cloud. Roddy Yes but it seems that all the values for a given property are pudhed into an array, then the occurences are counted. This isn't very efficient. Edit: just realized i misunderstood the function. Will get back tomorrow. Edited August 16, 2018 by ~Code&Anime~ Link to comment Share on other sites More sharing options...
~Code&Anime~ Posted August 16, 2018 Share Posted August 16, 2018 (edited) function selectAndList(propertyName, inputArr) { const propertyArr = []; inputArr.map(function(item) { propertyArr.push(item[propertyName]); }); return propertyArr; } function countOccurences(propertyArr, value){ const values =propertyArr.filter(function(prop){ return prop==value }) return values.length } function countOccurences(propertyArr){ const map=new Map() propertyArr.map(function(val){ if(map.has(val)){ map.set(val, map.get(val)+1) }else{ map.set(val, 0) } }) return map } Apologies for this previous misunderstanding. I have rewritten my code in addition as to not use arrow functions as you mentioned you are not familiar with this. I thought it best to mention this as this may be useful when looking up info online. This is how such works for information, this was introduced in ES6: function myFunc(val){ } const myFunc = (val)=>{ } You would call both with myFunc(val), this does not change. also you should use const and let instead of var, var is defined globally, even when within a function. I have rewritten the function to reduce time complexity. There is no need to create multiple arrays. I have also defined a function to count occurences for a given property value Edited August 16, 2018 by ~Code&Anime~ Link to comment Share on other sites More sharing options...
Recommended Posts
Create an account or sign in to comment
You need to be a member in order to leave a comment
Create an account
Sign up for a new account in our community. It's easy!
Register a new accountSign in
Already have an account? Sign in here.
Sign In Now