Last active
February 6, 2024 14:55
-
-
Save juliarose/3e6084ee577e28661dd7f085206fade3 to your computer and use it in GitHub Desktop.
hello world in JavaScript
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
const Filtered = Symbol('Filtered'); | |
const Break = Symbol('Break'); | |
class CharIterator { | |
constructor(string) { | |
this.string = string; | |
this.index = 0; | |
} | |
next() { | |
if (this.index < this.string.length) { | |
return this.string[this.index++]; | |
} | |
return Break; | |
} | |
map(fn) { | |
return new Map(this, fn); | |
} | |
filter(fn) { | |
return new Filter(this, fn); | |
} | |
collect() { | |
return collect(this); | |
} | |
} | |
class Split { | |
constructor(string, delimiter) { | |
this.iterator = new CharIterator(string); | |
this.delimiter = delimiter; | |
this.delimiterIndex = 0; | |
} | |
next() { | |
const index = this.iterator.index; | |
const char = this.iterator.next(); | |
if (char === Break) { | |
return Break; | |
} | |
while (true) { | |
const char = this.iterator.next(); | |
if (char === Filtered) { | |
continue; | |
} | |
if (char === Break) { | |
return this.iterator.string.slice(index, this.iterator.index); | |
} | |
if (char === this.delimiter.charAt(this.delimiterIndex)) { | |
this.delimiterIndex++; | |
if (this.delimiterIndex === this.delimiter.length) { | |
return this.iterator.string.slice(index, this.iterator.index - this.delimiter.length); | |
} | |
} else { | |
this.delimiterIndex = 0; | |
} | |
} | |
} | |
map(fn) { | |
return new Map(this, fn); | |
} | |
filter(fn) { | |
return new Filter(this, fn); | |
} | |
collect() { | |
return collect(this); | |
} | |
} | |
class Map { | |
constructor(iterator, fn) { | |
this.iterator = iterator; | |
this.fn = fn; | |
} | |
next() { | |
const value = this.iterator.next(); | |
if (isControl(value)) { | |
return value; | |
} | |
return this.fn(value); | |
} | |
map(fn) { | |
return new Map(this, fn); | |
} | |
filter(fn) { | |
return new Filter(this, fn); | |
} | |
collect() { | |
return collect(this); | |
} | |
} | |
class Filter { | |
constructor(iterator, fn) { | |
this.iterator = iterator; | |
this.fn = fn; | |
} | |
next() { | |
let value = this.iterator.next(); | |
if (isControl(value)) { | |
return value; | |
} | |
if (!this.fn(value)) { | |
return Filtered; | |
} | |
return value; | |
} | |
map(fn) { | |
return new Map(this, fn); | |
} | |
filter(fn) { | |
return new Filter(this, fn); | |
} | |
collect() { | |
return collect(this); | |
} | |
} | |
function isControl(value) { | |
return value === Filtered || value === Break; | |
} | |
function collect(iterator) { | |
let result = []; | |
while (true) { | |
let value = iterator.next(); | |
if (value === Break) { | |
break; | |
} | |
if (value === Filtered) { | |
continue; | |
} | |
result.push(value); | |
} | |
return result; | |
} | |
String.prototype.split = function(delimiter) { | |
return new Split(this, delimiter); | |
}; | |
let iterated = 'hello_ _world_ _how_ _are_ _you' | |
.split('_ _') | |
.map(value => value.toUpperCase()) | |
.filter(value => value.length > 3) | |
.map(value => value.toLowerCase()) | |
.collect() | |
.join(' ') | |
.split(' ') | |
.collect() | |
.join(' '); | |
console.log(iterated); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment