Skip to content

Commit

Permalink
Skyhigh173/json: add analysis block (#1907)
Browse files Browse the repository at this point in the history
this adds the same analysis support as data-analysis but into JSON (to
get rid of the need to do stuff like the image below)

![image](https://github.com/user-attachments/assets/13279167-e650-4e0f-9610-ea2f1d9a54a1)

---------

Co-authored-by: Cubester <[email protected]>
  • Loading branch information
yuri-kiss and CubesterYT authored Feb 7, 2025
1 parent f9a6b0f commit fe5c742
Showing 1 changed file with 110 additions and 1 deletion.
111 changes: 110 additions & 1 deletion extensions/Skyhigh173/json.js
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@
(function (Scratch) {
"use strict";
/*
* JSON extension v2.5 by skyhigh173 (English Version)
* JSON extension v2.6 by skyhigh173 (English Version)
* Do not remove this comment
*/

Expand Down Expand Up @@ -481,6 +481,22 @@
},
},
},
{
opcode: "json_array_analysis",
blockType: Scratch.BlockType.REPORTER,
text: Scratch.translate("[analysis] of array [list]"),
disableMonitor: true,
arguments: {
list: {
type: Scratch.ArgumentType.STRING,
defaultValue: "[17, 1, 2017, 0, 120, 14]",
},
analysis: {
type: Scratch.ArgumentType.STRING,
menu: "analysis",
},
},
},
makeLabel(Scratch.translate("Lists")),
{
opcode: "json_vm_getlist",
Expand Down Expand Up @@ -560,6 +576,39 @@
},
],
},
analysis: {
acceptReporters: true,
items: [
{
text: Scratch.translate("minimum value"),
value: "minimum",
},
{
text: Scratch.translate("maximum value"),
value: "maximum",
},
{
text: Scratch.translate("sum"),
value: "sum",
},
{
text: Scratch.translate("average"),
value: "average",
},
{
text: Scratch.translate("median"),
value: "median",
},
{
text: Scratch.translate("mode"),
value: "mode",
},
{
text: Scratch.translate("variance"),
value: "variance",
},
],
},
},
};
}
Expand Down Expand Up @@ -1008,6 +1057,66 @@
if (args.order === "descending") list.reverse();
return JSON.stringify(list);
}
json_array_analysis(args) {
let list;
try {
list = JSON.parse(args.list);
} catch {
return 0;
}
if (!Array.isArray(list)) {
return 0;
}
list = list.map(Scratch.Cast.toNumber);
const listLength = list.length;
switch (Scratch.Cast.toString(args.analysis)) {
case "maximum": {
let max = -Infinity;
for (let i = 0; i < list.length; i++)
if (list[i] > max) max = list[i];
return max;
}
case "minimum": {
let min = Infinity;
for (let i = 0; i < list.length; i++)
if (list[i] < min) min = list[i];
return min;
}
case "sum":
return list.reduce((a, b) => a + b, 0);
case "average":
return list.reduce((a, b) => a + b, 0) / listLength;
case "median": {
const list2 = list.sort(Scratch.Cast.compare);
const list2Length = list2.length;
const c = Math.floor(list2Length / 2);
const e = list2Length % 2 === 0;
if (e) return (list2[c - 1] + list2[c]) / 2;
return list2[c];
}
case "mode": {
const freqMap = new Map(),
mode = [0, 0]; // current mode, max
for (
let i = 0, num = list[0], count = null;
i < listLength;
i++, num = list[i], count = freqMap.get(num)
) {
count ||= 1;
if (freqMap.has(num)) ++count;
if (count > mode[1]) (mode[0] = num), (mode[1] = count);
freqMap.set(num, count);
}
return mode[0];
}
case "variance": {
const average = list.reduce((a, b) => a + b, 0) / listLength;
const list2 = list.map((a) => (a - average) ** 2);
return list2.reduce((a, b) => a + b, 0) / listLength;
}
}
return 0;
}
}
Scratch.extensions.register(new JSONS());
})(Scratch);

0 comments on commit fe5c742

Please sign in to comment.