Javascript average within multidimension array - javascript

I have a 2D array, sorted by names of students and their various 100m sprint sessions. A snippet of the data array may look like this...
Names Time(s)
ANDREWMICHEALSMITH 13.95
JOHNJAMESPETERSON 13.70
JOHNJAMESPETERSON 13.80
JOHNJAMESPETERSON 12.50
PETERMICHEALHEWITT 12.80
PETERMICHEALHEWITT 12.60
VICENTJAMESSMITH 13.10
VICENTJAMESSMITH 13.50
VICENTJAMESSMITH 13.80
VICENTJAMESSMITH 13.00
I'm desperately needing to convert the table to show student name, their average time and the number of timed sessions, the desirable result as per below...
Names Avg Time(s) Sessions
ANDREWMICHEALSMITH 13.95 1
JOHNJAMESPETERSON 13.33 3
PETERMICHEALHEWITT 12.70 2
VICENTJAMESSMITH 13.35 4
I have drafted a JavaScript code so far unfortunately fails at the very first if statement.
Cannot read property "0" from undefined.
The code also doesn't capture student with nth number of sessions, and no provision for number of sessions yet. Quite frankly my Java knowledge is so limited for the task at hand. I'm in desperate need of some help to get to the end result.
I'm truely grateful for any guidance.
StudentList.sort();
for (var i=0; i<StudentList.length; i++){
if(StudentList[i][0] == StudentList[i+1][0]){
if(StudentList[i+1][0] == StudentList[i+2][0]){
if(StudentList[i+2][0] == StudentList[i+3][0]){
if(StudentList[i+3][0] == StudentList[i+4][0]){
StudentList[i][1] = (StudentList[i][1]+StudentList[i+1][1]+StudentList[i+2][1]+StudentList[i+3][1]+StudentList[i+4][1])/5;
StudentList.splice(i+1,3);
}else{
StudentList[i][1] = (StudentList[i][1]+StudentList[i+1][1]+StudentList[i+2][1]+StudentList[i+3][1])/4;
}
}else{
StudentList[i][1] = (StudentList[i][1]+StudentList[i+1][1]+StudentList[i+2][1])/3;
}
}else{
StudentList[i][1] = (StudentList[i][1]+StudentList[i+1][1])/2;
}
}
}

You could use an object as hash table for names and us ean array as result set for counting and storing the data.
var studentList = [['ANDREWMICHEALSMITH', 13.95], ['VICENTJAMESSMITH', 13.00], ['PETERMICHEALHEWITT', 12.80], ['PETERMICHEALHEWITT', 12.60], ['VICENTJAMESSMITH', 13.10], ['JOHNJAMESPETERSON', 13.70], ['JOHNJAMESPETERSON', 12.50], ['VICENTJAMESSMITH', 13.50], ['JOHNJAMESPETERSON', 13.80], ['VICENTJAMESSMITH', 13.80]],
hash = Object.create(null),
result = [],
array;
studentList.forEach(function (a) {
if (!hash[a[0]]) {
hash[a[0]] = { name: a[0], sum: 0, count: 0, avg: 0 };
result.push(hash[a[0]]);
}
hash[a[0]].sum += a[1];
hash[a[0]].count++;
hash[a[0]].avg = (hash[a[0]].sum / hash[a[0]].count).toFixed(2);
});
array = result.map(function (a) {
return [a.name, a.avg, a.count];
});
console.log(array);
console.log(result);
.as-console-wrapper { max-height: 100% !important; top: 0; }

Related

Get "leaderboard" of list of numbers

I am trying to get a kind of "leaderboard" from a list of numbers. I was thinking of making an array with all the numbers like this
var array = [];
for (a = 0; a < Object.keys(wallets.data).length; a++) { //var wallets = a JSON (parsed) response code from an API.
if (wallets.data[a].balance.amount > 0) {
array.push(wallets.data[a].balance.amount)
}
}
//Add some magic code here that sorts the array into descending numbers
This is a great option, however I need some other values to come with the numbers (one string). That's why I figured JSON would be a better option than an array.
I just have no idea how I would implement this.
I would like to get a json like this:
[
[
"ETH":
{
"balance":315
}
],
[
"BTC":
{
"balance":654
}
],
[
"LTC":
{
"balance":20
}
]
]
And then afterwards being able to call them sorted descending by balance something like this:
var jsonarray[0].balance = Highest number (654)
var jsonarray[1].balance = Second highest number (315)
var jsonarray[2].balance = Third highest number (20)
If any of you could help me out or point me in the right direction I would appreciate it greatly.
PS: I need this to happen in RAW JS without any html or libraries.
You should sort the objects before making them a JSON. You can write your own function or use a lambda. See this [https://stackoverflow.com/questions/1129216/sort-array-of-objects-by-string-property-value]
Since you are dealing with cryptocurrency you can use the currency-code as a unique identifier.
Instead of an array, you can define an object with the currency as properties like this:
const coins = {
ETH: [300, 200, 500],
BTC: [20000, 15000, 17000]
}
then you can access each one and use Math.max or Math.min to grab the highest / lowest value of that hashmap. E.G. Math.max(coins.BTC)
And if you need to iterate over the coins you have Object.keys:
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/keys
Thank you all for your answer. I ended up using something like:
leaderboard = []
for (a = 0; a < Object.keys(wallets.data).length; a++) {
if (wallets.data[a].balance.amount > 0) {
leaderboard.push({"currency":wallets.data[a].balance.currency, "price":accprice}) //accprice = variable which contains the value of the userhold coins of the current coin in EUR
}
}
console.log(leaderboard.sort(sort_by('price', true, parseInt)));

Sort Nested Json Object based on value in for loop?

Hoping someone can help me out here or at least point me in the right direction. I have spent hours trying to get this sorted and I am lost.
The code below is just mock, my actual json is returned via AJAX using jquery. My problem is not sorting, but sorting on a nested json object.
I am trying to sort the json output based on cost. (lowest cost to highest), my attempts have failed and I cannot get this sorted. I keep getting "sort" is undefined.
Any help would be appreciated or if you can just point out what I am doing wrong here.
var json = '{"shipping_method":{"ups":{"title":"United Parcel Service","quote":{"12":{"code":"ups.12","title":"UPS 3 Day Select","cost":117.3,"tax_class_id":"0","text":"$117.30"},"13":{"code":"ups.13","title":"UPS Next Day Air Saver","cost":242.52,"tax_class_id":"0","text":"$242.52"},"14":{"code":"ups.14","title":"UPS Next Day Air Early A.M.","cost":279.95,"tax_class_id":"0","text":"$279.95"},"03":{"code":"ups.03","title":"UPS Ground","cost":54.62,"tax_class_id":"0","text":"$54.62"},"02":{"code":"ups.02","title":"UPS 2nd Day Air","cost":177.31,"tax_class_id":"0","text":"$177.31"},"01":{"code":"ups.01","title":"UPS Next Day Air","cost":248.08,"tax_class_id":"0","text":"$248.08"}},"sort_order":"","error":""}}}';
/*
This doesnt work and returns undefined.
json["shipping_method"]["quote"].sort(function(a, b) {
return a['cost'] > b['cost'];
});
// I found this example, but also didn't work.
custSort = (prop1, prop2 = null, direction = 'asc') => (e1, e2) => {
const a = prop2 ? e1[prop1][prop2] : e1[prop1],
b = prop2 ? e2[prop1][prop2] : e2[prop1],
sortOrder = direction === "asc" ? 1 : -1
return (a < b) ? -sortOrder : (a > b) ? //sortOrder : 0;
};
json.sort(custSort("quote", "cost", "desc"));*/
json = JSON.parse(json);
for (var i in json["shipping_method"]) {
// EDIT:: I want the sorting to occur here if possible.
for (j in json["shipping_method"][i]["quote"]) {
//EDIT:: I want to keep this for loop, but with the results sorted by cost
console.log(json["shipping_method"][i]["quote"][j]["cost"]);
}
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
Convert Object to Sorted Array
The object can be flattened out so that parent keys are included in the deep object as it's been iterated over. An early example to that can be found in this answers edit history. It has been removed since information like the quote-id was not deemed important.
Below is an example of using Object.values, which traverses an object and only returns an array of that objects values (discarding the keys). The values can then be sorted as intended, by cost.
const json = JSON.parse(getData());
for (let method in json["shipping_method"]) {
// cache
let quotes = json['shipping_method'][method]['quote']
// convert object to array and sort
let sortedQuotes = Object.values(quotes).sort((a, b)=>a.cost-b.cost);
console.log(sortedQuotes)
}
/* Dummy Data */
function getData() {
return '{"shipping_method":{"ups":{"title":"United Parcel Service","quote":{"12":{"code":"ups.12","title":"UPS 3 Day Select","cost":117.3,"tax_class_id":"0","text":"$117.30"},"13":{"code":"ups.13","title":"UPS Next Day Air Saver","cost":242.52,"tax_class_id":"0","text":"$242.52"},"14":{"code":"ups.14","title":"UPS Next Day Air Early A.M.","cost":279.95,"tax_class_id":"0","text":"$279.95"},"03":{"code":"ups.03","title":"UPS Ground","cost":54.62,"tax_class_id":"0","text":"$54.62"},"02":{"code":"ups.02","title":"UPS 2nd Day Air","cost":177.31,"tax_class_id":"0","text":"$177.31"},"01":{"code":"ups.01","title":"UPS Next Day Air","cost":248.08,"tax_class_id":"0","text":"$248.08"}},"sort_order":"","error":""}}}';
}
.as-console-wrapper {
max-height: 100vh !important;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
Quotes by Cost per Shipping Method
This assumes that the quote ID is needed (perhaps to be placed on a row); otherwise this can be simplified using Object.values in place of Object.entries (amongst other changes).
Disregard what the output function is doing. It is a quick example, that doesn't ensure proper cell order and has a host of other limitations and vulnerabilities. It is only used to demonstrate that the original quote data is still available after sorting.
const data = JSON.parse(getData());
for (let method in data.shipping_method) {
output({row: method}, {class:'capitalize'})
// cache
let quotes = data.shipping_method[method].quote
let sortContent = Object.entries(quotes);
let sortedQuotes = sortContent.sort((a,b)=>a[1].cost-b[1].cost).map(i=>i[0]);
for (let quoteId of sortedQuotes){
let quoteInfo = quotes[quoteId];
output({cell: quoteInfo})
}
}
/* Dummy Data */
function getData() {
return '{"shipping_method":{"ups":{"title":"United Parcel Service","quote":{"12":{"code":"ups.12","title":"UPS 3 Day Select","cost":117.3,"tax_class_id":"0","text":"$117.30"},"13":{"code":"ups.13","title":"UPS Next Day Air Saver","cost":242.52,"tax_class_id":"0","text":"$242.52"},"14":{"code":"ups.14","title":"UPS Next Day Air Early A.M.","cost":279.95,"tax_class_id":"0","text":"$279.95"},"03":{"code":"ups.03","title":"UPS Ground","cost":54.62,"tax_class_id":"0","text":"$54.62"},"02":{"code":"ups.02","title":"UPS 2nd Day Air","cost":177.31,"tax_class_id":"0","text":"$177.31"},"01":{"code":"ups.01","title":"UPS Next Day Air","cost":248.08,"tax_class_id":"0","text":"$248.08"}},"sort_order":"","error":""}}}';
}
/* Really simple output for demo purpose */
function output(data, options={}){
if ('row' in data){
let $col = $('<td></td>', options).html(data.row)
let $row = $('<tr></tr>').append($col);
$('tbody').append( $row )
}
else if ('cell' in data){
let $row = $('<tr></tr>')
for( let key in data.cell ){
let $col = $('<td></td>', options).html(data.cell[key])
$row.append($col)
}
$('tbody').append( $row )
}
}
.capitalize {
text-transform: uppercase;
}
td {
min-width: 5rem;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<table>
<thead></thead>
<tbody></tbody>
</table>
Your objects can have any amount of properties and you can choose to sort by whatever object property you want, number or string, if you put the objects in an array.
var item = JSON.parse(json).shipping_method.ups.quote;
Use Object.values() to get array of values of the JSON object and then use slice() method to copy the array of JSON objects and not just make a reference.
var byCost = Object.values(item).slice(0);
Finally you can use sort function for that array of objects.
byCost.sort(function(a,b) {return a.cost - b.cost});
var json = '{"shipping_method":{"ups":{"title":"United Parcel Service","quote":{"12":{"code":"ups.12","title":"UPS 3 Day Select","cost":117.3,"tax_class_id":"0","text":"$117.30"},"13":{"code":"ups.13","title":"UPS Next Day Air Saver","cost":242.52,"tax_class_id":"0","text":"$242.52"},"14":{"code":"ups.14","title":"UPS Next Day Air Early A.M.","cost":279.95,"tax_class_id":"0","text":"$279.95"},"03":{"code":"ups.03","title":"UPS Ground","cost":54.62,"tax_class_id":"0","text":"$54.62"},"02":{"code":"ups.02","title":"UPS 2nd Day Air","cost":177.31,"tax_class_id":"0","text":"$177.31"},"01":{"code":"ups.01","title":"UPS Next Day Air","cost":248.08,"tax_class_id":"0","text":"$248.08"}},"sort_order":"","error":""}}}';
var item = JSON.parse(json).shipping_method.ups.quote;
var byCost = Object.values(item).slice(0);
byCost.sort(function(a,b) {return a.cost - b.cost});
console.log(byCost)
It doesn't seem like you are accessing the right path here... Looking at the JSON you posted you should be attempting to sort shipping_method.ups.quote its also worth noting that shipping_method.ups.quote is an object and must be converted to an Array to invoke .sort as this method lives on the Array prototype.
This can be done several ways but Object.values() is one such way.
you may try the following,
json = JSON.parse(json);
let item = json.shipping_method.ups.quote,
temp = [];
for (let key in item) {
temp.push(item[key]);
}
temp.sort((x, y) => x.cost - y.cost);
json.shipping_method.ups.quote = temp;
converting your object into array and then sort;
As i can see , your problem is to sort the object with cost as their keys should stays same ,
try out this ,
var json = '{"shipping_method":{"ups":{"title":"United Parcel Service","quote":{"12":{"code":"ups.12","title":"UPS 3 Day Select","cost":117.3,"tax_class_id":"0","text":"$117.30"},"13":{"code":"ups.13","title":"UPS Next Day Air Saver","cost":242.52,"tax_class_id":"0","text":"$242.52"},"14":{"code":"ups.14","title":"UPS Next Day Air Early A.M.","cost":279.95,"tax_class_id":"0","text":"$279.95"},"03":{"code":"ups.03","title":"UPS Ground","cost":54.62,"tax_class_id":"0","text":"$54.62"},"02":{"code":"ups.02","title":"UPS 2nd Day Air","cost":177.31,"tax_class_id":"0","text":"$177.31"},"01":{"code":"ups.01","title":"UPS Next Day Air","cost":248.08,"tax_class_id":"0","text":"$248.08"}},"sort_order":"","error":""}}}';
var json = JSON.parse(json);
let data = []
for(var i in json.shipping_method.ups.quote){
data.push(json.shipping_method.ups.quote[i])
data.sort((a,b) => a.cost - b.cost);
}
This create those key agains as they are before
let final = {} ;
data.forEach(el => final[el.code.split('.')[1]] = el);
Finally update the qoute with the latest sorted quotes :
json.shipping_method.ups.quote = final;

How to find the position of all array items from a loop

I'm brand new to programming so I apologize if this is a simple question.
I had a unique practice problem that I'm not quite sure how to solve:
I'm dealing with two arrays, both arrays are pulled from HTML elements on the page, one array is representing a bunch of states, and the next array is representing their populations. The point of the problem is to print the name of the states and their less than average populations.
To find and print all of the populations that are less than the average I used this code:
function code6() {
// clears screen.
clr();
// both variables pull data from HTML elements with functions.
var pop = getData2();
var states = getData();
var sum = 0;
for( var i = 0; i < pop.length; i++ ){
sum += parseInt( pop[i], 10 );
var avg = sum/pop.length;
if (pop[i] < avg) {
println(pop[i]);
// other functions used in the code to get data, print, and clear the screen.
function getData() {
var dataSource = getElement("states");
var numberArray = dataSource.value.split('\n');
// Nothing to split returns ['']
if (numberArray[0].length > 0) {
return(numberArray);
} else {
return [];
}
}
// Get the data from second data column
function getData2() {
var dataSource = getElement("pops");
var numberArray = dataSource.value.split('\n');
// Nothing to split returns ['']
if (numberArray[0].length > 0) {
return(numberArray);
} else {
return [];
}
}
// Clear the 'output' text area
function clr() {
var out = getElement("output");
out.value = "";
}
// Print to the 'output' HTML element and ADDS the line break
function println(x) {
if (arguments.length === 0) x = '';
print(x + '\n');
}
Now I just need to know how to get the value of these positions within the array so I can pull out the same positions from my states array and display them both side by side. Both arrays have the identical amount of items.
I hope this makes sense and thanks in advance to anyone who has time to take a look at this.
Best regards,
-E
Its a little hard to tell what you are trying to accomplish, but I guess you are going for something like:
'use strict'
function code6() {
const populations = ['39000000', '28000000', '21000000'];
const stateNames = ['california', 'texas', 'florida'];
const states = populations.map((population, i) => ({
'name': stateNames[i],
'population': Number(population),
}));
const sum = states.reduce((sum, state) => sum + state.population, 0);
const average = sum / populations.length;
states
.filter(state => state.population < average)
.forEach(state => {
const name = state.name;
const population = state.population;
console.log(`state name: ${name}, population: ${population}`);
});
}
// run the code
code6();
// state name: texas, population: 28000000
// state name: florida, population: 21000000
I took the liberty of refactoring your code to be a little more modern (es6) and Idiomatic. I hope its not to confusing for you. Feel free to ask any questions about it.
In short you should use:
'use strict' at the top of your files
const/let
use map/filter/forEach/reduce to iterate lists.
use meaningfull names
, and you should avoid:
classic indexed for-loop
parseInt
, and pretty much never ever use:
var
If your states array is built with corresponding indices to your pop one, like this:
states; //=> ['Alabama', 'Alaska', 'Arizona', ...]
pop; //=> [4863300, 741894, 6931071, ...]
then you could simply update your print statement to take that into account:
if (pop[i] < avg) {
println(state[i] + ': ' + pop[i]);
}
Or some such.
However, working with shared indices can be a very fragile way to use data. Could you rethink your getData and getData2 functions and combine them into one that returns a structure more like this the following?
states; //=> [
// {name: 'Alabama', pop: 4863300}
// {name: 'Alaska', pop: 741894},
// {name: 'Arizona', pop: 6931071},
// ...]
This would entail changes to the code above to work with the pop property of these objects, but it's probably more robust.
If your pop and state looks like:
var state = ['state1', 'state2', ...];
var pop = ['state1 pop', 'state2 pop', ...];
Then first of all, avg is already wrong. sum's value is running along with the loop turning avg's formula into sum as of iteration / array length instead of sum of all pops / array length. You should calculate the average beforehand. array.reduce will be your friend.
var average = pop.reduce(function(sum, val){return sum + val;}, 0) / pop.length;
Now for your filter operation, you can:
Zip up both arrays to one array using array.map.
Filter the resulting array with array.filter.
Finally, loop through the resulting array using array.forEach
Here's sample code:
var states = ['Alabama', 'Alaska'];
var pop = [4863300, 741894];
var average = pop.reduce(function(sum, val){return sum + val;}) / pop.length;
console.log('Average: ' + average);
states.map(function(state, index) {
// Convert 2 arrays to an array of objects representing state info
return { name: state, population: pop[index] };
}).filter(function(stateInfo) {
console.log(stateInfo);
// Filter each item by returning true on items you want to include
return stateInfo.population < average;
}).forEach(function(stateInfo) {
// Lastly, loop through your results
console.log(stateInfo.name + ' has ' + stateInfo.population + ' people');
});

Generating a price per item in an html table using a javascript

I have a javascript that is generating a table for me. The elements in the table are gathered in an array of arrays called sep. Sep contains 1152 sub arrays that are of the form:
Sep[0] //["316SS", "K", "-100 to 225°C", "Brass", "1/8", "4'", "4'", "8", "Ungrounded"]
So basically there are 1152 rows, each of which defines a products with 9 parameters. I want to make a for-loop that will create a price for each of the configurations. This is what I have so far:
//PART 1-------------WORKS FINE-----------------------------------
var eopartprice2 = []; //matrix that I want to contain my prices
for (var i = 0; i < sep.length; i++) {
strnum1 = sep[i][5]; //parameter 5 is a length of material
len1 = Number(strnum1.substr(0, strnum1.length - 1));
strnum2 = sep[i][6]; //parameter 6 is another length of material
len2 = Number(strnum2.substr(0, strnum2.length - 1));
strnum3 = sep[i][7]; //parameter 7 is the number of units required
condnum = Number(strnum3.substr(0, strnum3.length));
feetOfMat = len1*len2*condnum; //The product of these is the total feet of req material
//PART 2------------PFCost always = 0.87--------------------------
//Next i need to identify the cost of the material (to multiply by the total feet)
var costOfMat = [0.87, 0.87, 1.77, 0.55] //different costs of the 4 materials
if (sep[i][0] = "304SS") {
var PFCost = costOfMat[0]; //304SS costs 0.87/foot
} else if (sep[i][0] = "316SS") {
var PFCost = costOfMat[1]; //316SS costs 0.87/foot
} else if (sep[i][0] = "Inconel") {
var PFCost = costOfMat[2]; //Inconel costs 1.77/foot
} else if (sep[i][0] = "High Temp. Glass") {
var PFCost = costOfMat[3]; //High Temp. Glass costs 0.55/foot
}
baseMatCost[i] = PFCost*feetOfMat; //I'd like to generate a matrix that
//contains all of the base prices (1 for each row)
//PART 3---------------fitcost always = 36------------------------
//Trying to identify the cost of brass vs. stainless fittings
if (sep[i][3] = "Brass") {
fitcost = 36;
} else if (sep[i][3] = "Stainless Steel") {
fitcost = 37;
}
}
My Problem so far is that I want the prices to be defined based off of whether or not the if statements are satisfied but in both cases (fitcost and PFCost) the values are simply the ones defined in the first if statement.
Lastly I'd like to generate my final price in the eopartprice2 matrix based off adding up the materials generated above + some cost of labor multiplied by some margin.
Also I'm concerned with the speed of how quickly this runs as it will be a live table in my website, and every time I add more to this I feel like it's taking longer and longer to generate. Here's a link to my w3 that I'm working in.
Please, any help would be greatly appreciated :)
In your if statement conditions, you're using a single equals sign. This is an assignment operator, not a comparison operator!
So, an if statement such as if (sep[i][0] = "304SS") is actually assigning the value "304SS"; it is not comparing the value "304SS" to sep[i][0].
To correctly compare the values, you'll want to change the single equals sign to a double equals:
if (sep[i][0] == "304SS").
Note: == will convert types if necessary before comparing. For example: ".87" == 0.87 returns true.

Couchbase, reduction too large error

On my work I using couchbase and I have some problems. From some devices data come to couchbase, and after I calling aggregate view. This view must aggregate values by 2 keys: timestamp and deviceId.
Everything was fine, before I have tried to aggregate more then 10k values. In this case I have reduction error
Map function:
function(doc, meta)
{
if (doc.type == "PeopleCountingIn"&& doc.undefined!=true)
{
emit(doc.id+"#"+doc.time, [doc.in, doc.out, doc.id, doc.time, meta.id]);
}
}
Reduce function:
function(key, values, rereduce)
{
var result =
{
"id":0,
"time":0,
"in" : 0,
"out" : 0,
"docs":[]
};
if (rereduce)
{
result.id=values[0].id;
result.time = values[0].time;
for (i = 0; i<values.length; i++)
{
result.in = result.in + values[i].in;
result.out = result.out + values[i].out;
for (j = 0; j < values[i].docs.length; j++)
{
result.docs.push(values[i].docs[j]);
}
}
}
else
{
result.id = values[0][2];
result.time = values[0][3];
for(i = 0; i < values.length; i++)
{
result.docs.push(values[i][4]);
result.in = result.in + values[i][0];
result.out = result.out + values[i][1];
}
}
return result;
}
Document sample:
{
"id": "12292228#0",
"time": 1401431340,
"in": 0,
"out": 0,
"type": "PeopleCountingIn"
}
UPDATE
Output document:
{"rows":[
{"key":"12201774#0#1401144240","value":{"id":"12201774#0","time":1401144240,"in":0,"out":0,"docs":["12231774#0#1401546080#1792560127"]}},
{"key":"12201774#0#1401202080","value":{"id":"12201774#0","time":1401202080,"in":0,"out":0,"docs":["12201774#0#1401202080#1792560840"]}}
]
}
}
Error occurs in the case where "docs" array length more then 100. And I think in that cases working rereduce function. Is there some way to fix this error exept making count of this array less?
There are a number of limits on the output of map & reduce functions, to prevent indexes taking too long and/or growing too large.
These are in the process of being added to the official documentation, but in the meantime quoting from the issue (MB-11668) tracking the documentation update:
1) indexer_max_doc_size - documents larger then this value are skipped by the
indexer. A message is logged (with document ID, its size, bucket name, view name, etc)
when such a document is encountered. A value of 0 means no limit (like what it used to
be before). Current default value is 1048576 bytes (1Mb).
2) max_kv_size_per_doc - maximum total size (bytes) of KV pairs that can be emitted for
a single document for a single view. When such limit is passed, message is logged (with
document ID, its size, bucket name, view name, etc). A value of 0 means no limit (like what
it used to be before). Current default value is 1048576 bytes (1Mb)
Edit: Additionally, there is a limit of 64kB for the size of a single reduction (output of the reduce(). I suggest you re-work your reduce function to return data within this limit. See MB-7952 for a technical discussion on why this is the case.

Categories

Resources