Brace expansion using ranges: Difference between revisions

Content added Content deleted
(Updated and fixed Python in line with new task example.)
(→‎{{header|JavaScript}}: Updated primitives)
Line 527: Line 527:


return 0 < expansions.length ? (() => {
return 0 < expansions.length ? (() => {
const [parsed, residue] = Array.from(
const [parsed, residue] = expansions[0];
expansions[0]
);


return suffixAdd(
return suffixAdd(
Line 584: Line 582:
];
];


return tests.map(
return tests.map(s => {
s => {
const
const
expanded = braceExpandWithRange(s)
expanded = braceExpandWithRange(s)
.join("\n\t");
.join("\n\t");


return `${s} -> \n\t${expanded}`;
return `${s} -> \n\t${expanded}`;
}
})
)
.join("\n\n");
.join("\n\n");
};
};
Line 773: Line 769:
p => Parser(
p => Parser(
s => parse(pf)(s).flatMap(
s => parse(pf)(s).flatMap(
vr => parse(
([v, r]) => parse(
fmapP(vr[0])(p)
fmapP(v)(p)
)(vr[1])
)(r)
)
)
);
);
Line 804: Line 800:
f => Parser(
f => Parser(
s => parse(p)(s).flatMap(
s => parse(p)(s).flatMap(
tpl => parse(f(tpl[0]))(tpl[1])
([x, r]) => parse(f(x))(r)
)
)
);
);
Line 847: Line 843:
p => Parser(
p => Parser(
s => parse(p)(s).flatMap(
s => parse(p)(s).flatMap(
vr => Tuple(f(vr[0]))(vr[1])
first(f)
)
)
);
);
Line 855: Line 851:
const item = () =>
const item = () =>
// A single character.
// A single character.
Parser(
Parser(s => {
s => 0 < s.length ? [
const [h, ...t] = s;

Tuple(s[0])(
s.slice(1)
return Boolean(h) ? [
)
Tuple(h)(t)
] : []
] : [];
);
});




Line 922: Line 918:
// Any character for which the
// Any character for which the
// given predicate returns true.
// given predicate returns true.
Parser(
Parser(s => {
s => 0 < s.length ? (
const [h, ...t] = s;

test(s[0]) ? [
Tuple(s[0])(s.slice(1))
return Boolean(h) ? (
test(h) ? [
Tuple(h)(t)
] : []
] : []
) : []
) : [];
);
});


// sequenceP :: [Parser a] -> Parser [a]
// sequenceP :: [Parser a] -> Parser [a]
Line 937: Line 935:
s => ps.reduce(
s => ps.reduce(
(a, q) => a.flatMap(
(a, q) => a.flatMap(
vr => parse(q)(snd(vr)).flatMap(
([v, r]) => parse(q)(r).flatMap(
first(xs => fst(vr).concat(xs))
first(xs => v.concat(xs))
)
)
),
),
Line 980: Line 978:
"0": a,
"0": a,
"1": b,
"1": b,
length: 2
length: 2,
*[Symbol.iterator]() {
for (const k in this) {
if (!isNaN(k)) {
yield this[k];
}
}
}
});
});



// abs :: Num -> Num
// abs :: Num -> Num
Line 1,019: Line 1,025:


// concat :: [[a]] -> [a]
// concat :: [[a]] -> [a]
// concat :: [String] -> String
const concat = xs =>
const concat = xs => (
xs.flat(1);
ys => 0 < ys.length ? (
ys.every(Array.isArray) ? (
[]
) : ""
).concat(...ys) : ys
)(list(xs));




Line 1,059: Line 1,059:
// A simple function lifted to one which applies
// A simple function lifted to one which applies
// to a tuple, transforming only its first item.
// to a tuple, transforming only its first item.
xy => Tuple(f(xy[0]))(
([x, y]) => Tuple(f(x))(y);
xy[1]
);




Line 1,071: Line 1,069:
(a, b) => op(b, a)
(a, b) => op(b, a)
) : (x => y => op(y)(x));
) : (x => y => op(y)(x));


// fst :: (a, b) -> a
const fst = tpl =>
// First member of a pair.
tpl[0];




Line 1,109: Line 1,101:
s.padStart(n, c)
s.padStart(n, c)
) : s;
) : s;


// list :: StringOrArrayLike b => b -> [a]
const list = xs =>
// xs itself, if it is an Array,
// or an Array derived from xs.
Array.isArray(xs) ? (
xs
) : Array.from(xs || []);




Line 1,179: Line 1,162:
const reverse = xs =>
const reverse = xs =>
xs.slice(0).reverse();
xs.slice(0).reverse();


// snd :: (a, b) -> b
const snd = tpl =>
// Second member of a pair.
tpl[1];




Line 1,202: Line 1,179:
return "number" !== t ? (
return "number" !== t ? (
(() => {
(() => {
const [i, mx] = [x, maxBound(x)].map(fromEnum);
const [i, mx] = [x, maxBound(x)].map(
fromEnum
);


return i < mx ? (
return i < mx ? (