structurae
Advanced tools
Comparing version 4.0.0-pre.6 to 4.0.0-pre.7
@@ -14,2 +14,3 @@ import type { ComplexView, ContainerView, PrimitiveView, ViewConstructor, ViewInstance } from "./view-types"; | ||
[Symbol.iterator](): Iterator<ViewInstance<T>>; | ||
at(index: number): T; | ||
get(index: number): T; | ||
@@ -16,0 +17,0 @@ getLength(_: number): number; |
@@ -50,2 +50,7 @@ export class ArrayView extends DataView { | ||
} | ||
at(index) { | ||
if (index < 0) | ||
return this.get(this.size + index); | ||
return this.get(index); | ||
} | ||
get(index) { | ||
@@ -52,0 +57,0 @@ const constructor = this.constructor; |
@@ -29,3 +29,3 @@ export { AdjacencyListMixin } from "./adjacency-list"; | ||
export { VectorView } from "./vector-view"; | ||
export type { ViewConstructor, ViewInstance } from "./view-types"; | ||
export type { ViewConstructor, ViewInstance, ViewSchema, } from "./view-types"; | ||
export { View } from "./view"; |
{ | ||
"name": "structurae", | ||
"version": "4.0.0-pre.6", | ||
"version": "4.0.0-pre.7", | ||
"description": "Data structures for performance-sensitive modern JavaScript applications.", | ||
@@ -5,0 +5,0 @@ "main": "index.js", |
337
README.md
@@ -57,3 +57,3 @@ # Structurae | ||
``` | ||
import {...} from "https://deno.land/x/structurae@4.0.0-pre.5/index.ts" | ||
import {...} from "https://deno.land/x/structurae@4.0.0-pre.7/index.ts" | ||
``` | ||
@@ -74,7 +74,7 @@ | ||
Binary data in JavaScript is represented by ArrayBuffer and accessed through | ||
"view" interfaces--TypedArrays and DataView. However, both of those interfaces | ||
are limited to working with numbers. Structurae offers a set of classes that | ||
extend the DataView interface to support using ArrayBuffers for strings, | ||
objects, and arrays. These classes ("views") form the basis for a simple binary | ||
protocol ("view protocol") with the following features: | ||
TypedArrays and DataView. However, both of those interfaces are limited to | ||
working with numbers. Structurae offers a set of classes that extend the | ||
DataView interface to support using ArrayBuffers for strings, objects, and | ||
arrays. These classes ("views") form the basis for a simple binary protocol with | ||
the following features: | ||
@@ -112,11 +112,7 @@ - smaller and faster than schema-less binary formats (e.g. BSON, MessagePack); | ||
const animal = AnimalView.from({ name: "Gaspode", age: 10 }); | ||
animal instanceof DataView; | ||
//=> true | ||
animal.byteLength; | ||
//=> 14 | ||
animal.get("age"); | ||
//=> 10 | ||
animal instanceof DataView; //=> true | ||
animal.byteLength; //=> 14 | ||
animal.get("age"); //=> 10 | ||
animal.set("age", 20); | ||
animal.toJSON(); | ||
//=> { name: "Gaspode", age: 20 } | ||
animal.toJSON(); //=> { name: "Gaspode", age: 20 } | ||
``` | ||
@@ -175,8 +171,5 @@ | ||
}); | ||
person.get("name"); | ||
//=> Carrot | ||
person.getView("name"); | ||
//=> StringView [10] | ||
person.get("fullName"); | ||
//=> ["Carrot", "Ironfoundersson"] | ||
person.get("name"); //=> Carrot | ||
person.getView("name"); //=> StringView [10] | ||
person.get("fullName"); //=> ["Carrot", "Ironfoundersson"] | ||
person.toJSON(); | ||
@@ -265,4 +258,3 @@ //=> { | ||
const house = House.from({} as House); | ||
house.get("size"); | ||
//=> 100 | ||
house.get("size"); //=> 100 | ||
``` | ||
@@ -287,6 +279,4 @@ | ||
const neighborhood = Neighborhood.from({} as Neighborhood); | ||
neighborhood.get("house"); | ||
//=> { size: 100 } | ||
neighborhood.get("biggerHouse"); | ||
//=> { size: 200 } | ||
neighborhood.get("house"); //=> { size: 100 } | ||
neighborhood.get("biggerHouse"); //=> { size: 200 } | ||
``` | ||
@@ -355,32 +345,24 @@ | ||
//=> StringView [ 97, 98, 99, 240, 159, 152, 128, 97 ] | ||
stringView.toString(); | ||
//=> "abc😀a" | ||
stringView == "abc😀a"; | ||
//=> true | ||
stringView.toString(); //=> "abc😀a" | ||
stringView == "abc😀a"; //=> true | ||
stringView = StringView.from("abc😀"); | ||
stringView.length; // length of the view in bytes | ||
//=> 8 | ||
stringView.size; // the amount of characters in the string | ||
//=> 4 | ||
stringView.charAt(0); // get the first character in the string | ||
//=> "a" | ||
stringView.charAt(3); // get the fourth character in the string | ||
//=> "😀" | ||
[...stringView.characters()]; // iterate over characters | ||
//=> ["a", "b", "c", "😀"] | ||
stringView.substring(0, 4); | ||
//=> "abc😀" | ||
// length of the view in bytes | ||
stringView.length; //=> 8 | ||
// the amount of characters in the string | ||
stringView.size; //=> 4 | ||
// get the first character in the string | ||
stringView.charAt(0); //=> "a" | ||
// get the fourth character in the string | ||
stringView.charAt(3); //=> "😀" | ||
// iterate over characters | ||
[...stringView.characters()]; //=> ["a", "b", "c", "😀"] | ||
stringView.substring(0, 4); //=> "abc😀" | ||
stringView = StringView.from("abc😀a"); | ||
const searchValue = StringView.from("😀"); | ||
stringView.search(searchValue); // equivalent of String#indexOf | ||
//=> 3 | ||
stringView.indexOf(searchValue); //=> 3 | ||
const replacement = StringView.from("d"); | ||
stringView.replace(searchValue, replacement).toString(); | ||
//=> "abcda" | ||
stringView.reverse().toString(); | ||
//=> "adcba" | ||
stringView.replace(searchValue, replacement).toString(); //=> "abcda" | ||
stringView.reverse().toString(); //=> "adcba" | ||
``` | ||
@@ -483,8 +465,5 @@ | ||
const bitfield = new BitField(29); // 29 === 0b11101 | ||
bitfield.get(0); | ||
//=> 1 | ||
bitfield.get(1); | ||
//=> 0 | ||
bitfield.has(2, 3, 4); | ||
//=> true | ||
bitfield.get(0); //=> 1 | ||
bitfield.get(1); //=> 0 | ||
bitfield.has(2, 3, 4); //=> true | ||
``` | ||
@@ -498,11 +477,7 @@ | ||
const field = new Field({ width: 100, height: 200 }); | ||
field.get("width"); | ||
//=> 100; | ||
field.get("height"); | ||
//=> 200 | ||
field.get("width"); //=> 100; | ||
field.get("height"); //=> 200 | ||
field.set("width", 18); | ||
field.get("width"); | ||
//=> 18 | ||
field.toObject(); | ||
//=> { width: 18, height: 200 } | ||
field.get("width"); //=> 18 | ||
field.toObject(); //=> { width: 18, height: 200 } | ||
``` | ||
@@ -518,6 +493,4 @@ | ||
const largeField = new LargeField([1048576, 1048576]); | ||
largeField.value; | ||
//=> 1099512676352n | ||
largeField.set("width", 1000).get("width"); | ||
//=> 1000 | ||
largeField.value; //=> 1099512676352n | ||
largeField.set("width", 1000).get("width"); //=> 1000 | ||
``` | ||
@@ -536,8 +509,5 @@ | ||
const newField = new NewField(oldField); | ||
newField.get("width"); | ||
//=> 20 | ||
newField.get("height"); | ||
//=> 1 | ||
newField.set("weight", 100).get("weight"); | ||
//=> 100 | ||
newField.get("width"); //=> 20 | ||
newField.get("height"); //=> 1 | ||
newField.set("weight", 100).get("weight"); //=> 100 | ||
``` | ||
@@ -552,10 +522,5 @@ | ||
Field.encode([20, 1]); | ||
//=> 41 | ||
Field.encode({ height: 1, width: 20 }); | ||
//=> 41 | ||
Field.decode(41); | ||
//=> { width: 20, height: 1 } | ||
Field.encode([20, 1]); //=> 41 | ||
Field.encode({ height: 1, width: 20 }); //=> 41 | ||
Field.decode(41); //=> { width: 20, height: 1 } | ||
``` | ||
@@ -567,4 +532,3 @@ | ||
```javascript | ||
BitField.getMinSize(100); | ||
//=> 7 | ||
BitField.getMinSize(100); //=> 7 | ||
const Field = BitFieldMixin({ width: BitField.getMinSize(250), height: 8 }); | ||
@@ -581,6 +545,4 @@ ``` | ||
Field.isValid({ width: 100 }); | ||
//=> true | ||
Field.isValid({ width: 100, height: 3 }); | ||
//=> false | ||
Field.isValid({ width: 100 }); //=> true | ||
Field.isValid({ width: 100, height: 3 }); //=> false | ||
``` | ||
@@ -594,10 +556,6 @@ | ||
const field = new Field([20, 1]); | ||
field.match({ width: 20 }); | ||
//=> true | ||
field.match({ height: 1, width: 20 }); | ||
//=> true | ||
field.match({ height: 1, width: 19 }); | ||
//=> false | ||
Field.match(field.valueOf(), { height: 1, width: 20 }); | ||
//=> true | ||
field.match({ width: 20 }); //=> true | ||
field.match({ height: 1, width: 20 }); //=> true | ||
field.match({ height: 1, width: 19 }); //=> false | ||
Field.match(field.valueOf(), { height: 1, width: 20 }); //=> true | ||
``` | ||
@@ -612,6 +570,4 @@ | ||
const matcher = Field.getMatcher({ height: 1, width: 20 }); | ||
Field.match(new Field([20, 1]).valueOf(), matcher); | ||
//=> true | ||
Field.match(new Field([19, 1]).valueOf(), matcher); | ||
//=> false | ||
Field.match(new Field([20, 1]).valueOf(), matcher); //=> true | ||
Field.match(new Field([19, 1]).valueOf(), matcher); //=> false | ||
``` | ||
@@ -626,10 +582,6 @@ | ||
const array = new BitArray(10); | ||
array.getBit(0); | ||
//=> 0 | ||
array.setBit(0).getBit(0); | ||
//=> 1 | ||
array.size; | ||
//=> 10 | ||
array.length; | ||
//=> 1 | ||
array.getBit(0); //=> 0 | ||
array.setBit(0).getBit(0); //=> 1 | ||
array.size; //=> 10 | ||
array.length; //=> 1 | ||
``` | ||
@@ -656,14 +608,9 @@ | ||
// get the next available index and make it unavailable | ||
pool.get(); | ||
//=> 0 | ||
pool.get(); | ||
//=> 1 | ||
pool.get(); //=> 0 | ||
pool.get(); //=> 1 | ||
// set index available | ||
pool.free(0); | ||
pool.get(); | ||
//=> 0 | ||
pool.get(); | ||
//=> 2 | ||
pool.get(); //=> 0 | ||
pool.get(); //=> 2 | ||
``` | ||
@@ -681,8 +628,5 @@ | ||
array.setBit(1).setBit(3).setBit(7); | ||
array.rank(2); | ||
//=> 1 | ||
array.rank(7); | ||
//=> 2 | ||
array.select(2); | ||
//=> 3 | ||
array.rank(2); //=> 1 | ||
array.rank(7); //=> 2 | ||
array.select(2); //=> 3 | ||
``` | ||
@@ -715,4 +659,3 @@ | ||
// the length of a weighted graph is vertices + edges * 2 + 1 | ||
graph.length; | ||
//=> 19 | ||
graph.length; //=> 19 | ||
graph.addEdge(0, 1, 5); | ||
@@ -722,14 +665,8 @@ graph.addEdge(0, 2, 1); | ||
graph.addEdge(2, 5, 2); | ||
graph.hasEdge(0, 1); | ||
//=> true | ||
graph.hasEdge(0, 4); | ||
//=> false | ||
graph.outEdges(2); | ||
//=> [4, 5] | ||
graph.inEdges(2); | ||
//=> [0] | ||
graph.hasEdge(0, 1); | ||
//=> true | ||
graph.getEdge(0, 1); | ||
//=> 5 | ||
graph.hasEdge(0, 1); //=> true | ||
graph.hasEdge(0, 4); //=> false | ||
graph.outEdges(2); //=> [4, 5] | ||
graph.inEdges(2); //=> [0] | ||
graph.hasEdge(0, 1); //=> true | ||
graph.getEdge(0, 1); //=> 5 | ||
``` | ||
@@ -765,19 +702,12 @@ | ||
unweightedMatrix.addEdge(2, 5); | ||
unweightedMatrix.hasEdge(0, 1); | ||
//=> true | ||
unweightedMatrix.hasEdge(0, 4); | ||
//=> false | ||
unweightedMatrix.outEdges(2); | ||
//=> [4, 5] | ||
unweightedMatrix.inEdges(2); | ||
//=> [0] | ||
unweightedMatrix.hasEdge(0, 1); //=> true | ||
unweightedMatrix.hasEdge(0, 4); //=> false | ||
unweightedMatrix.outEdges(2); //=> [4, 5] | ||
unweightedMatrix.inEdges(2); //=> [0] | ||
const weightedMatrix = Matrix.create(6); | ||
weightedMatrix.addEdge(0, 1, 3); | ||
weightedMatrix.hasEdge(0, 1); | ||
//=> true | ||
weightedMatrix.hasEdge(1, 0); | ||
//=> false | ||
weightedMatrix.getEdge(1, 0); | ||
//=> 3 | ||
weightedMatrix.hasEdge(0, 1); //=> true | ||
weightedMatrix.hasEdge(1, 0); //=> false | ||
weightedMatrix.getEdge(1, 0); //=> 3 | ||
``` | ||
@@ -821,12 +751,9 @@ | ||
// a BFS traversal results | ||
[...graph.traverse()]; | ||
//=> [0, 1, 2, 3, 4, 5] | ||
[...graph.traverse()]; //=> [0, 1, 2, 3, 4, 5] | ||
// DFS | ||
[...graph.traverse(true)]; | ||
//=> [0, 3, 2, 5, 4, 1] | ||
[...graph.traverse(true)]; //=> [0, 3, 2, 5, 4, 1] | ||
// BFS yeilding only non-encountered ("white") vertices starting from 0 | ||
[...graph.traverse(false, 0, false, true)]; | ||
//=> [1, 2, 3, 4, 5] | ||
[...graph.traverse(false, 0, false, true)]; //=> [1, 2, 3, 4, 5] | ||
``` | ||
@@ -858,8 +785,5 @@ | ||
bitGrid.setValue(0, 0).setValue(0, 2).setValue(0, 5); | ||
bitGrid.getValue(0, 0); | ||
//=> 1 | ||
bitGrid.getValue(0, 1); | ||
//=> 0 | ||
bitGrid.getValue(0, 2); | ||
//=> 1 | ||
bitGrid.getValue(0, 0); //=> 1 | ||
bitGrid.getValue(0, 1); //=> 0 | ||
bitGrid.getValue(0, 2); //=> 1 | ||
``` | ||
@@ -885,6 +809,4 @@ | ||
const grid = ArrayGrid.create(5, 4); | ||
grid.length; | ||
//=> 20 | ||
grid[0]; | ||
//=> 0 | ||
grid.length; //=> 20 | ||
grid[0]; //=> 0 | ||
@@ -904,9 +826,7 @@ // create a grid from existing data: | ||
dataGrid.columns = 4; | ||
dataGrid.getValue(1, 0); | ||
//=> 5 | ||
dataGrid.getValue(1, 0); //=> 5 | ||
// you can change dimensions of the grid by setting columns number at any time: | ||
dataGrid.columns = 2; | ||
dataGrid.getValue(1, 0); | ||
//=> 3 | ||
dataGrid.getValue(1, 0); //=> 3 | ||
``` | ||
@@ -918,17 +838,12 @@ | ||
//=> ArrayGrid [1, 2, 3, 4, 5, 6, 7, 8] | ||
grid.getValue(0, 1); | ||
//=> 2 | ||
grid.getValue(0, 1); //=> 2 | ||
grid.setValue(0, 1, 10); | ||
grid.getValue(0, 1); | ||
//=> 10 | ||
grid.getValue(0, 1); //=> 10 | ||
// use `getIndex` to get an array index of an element at given coordinates | ||
grid.getIndex(0, 1); | ||
//=> 1 | ||
grid.getIndex(0, 1); //=> 1 | ||
// use `getCoordinates` to find out row and column indexes of a given element by its array index: | ||
grid.getCoordinates(0); | ||
//=> [0, 0] | ||
grid.getCoordinates(1); | ||
//=> [0, 1] | ||
grid.getCoordinates(0); //=> [0, 0] | ||
grid.getCoordinates(1); //=> [0, 1] | ||
``` | ||
@@ -942,4 +857,3 @@ | ||
//=> ArrayGrid [ 1, 2, 3, 4 ] | ||
grid.getValue(1, 1); | ||
//=> 4 | ||
grid.getValue(1, 1); //=> 4 | ||
@@ -950,11 +864,7 @@ // if arrays are not the same size or their size is not equal to a power two, Grid will pad them with 0 by default | ||
//=> ArrayGrid [ 1, 2, 0, 0, 3, 4, 5, 0 ] | ||
grid.getValue(1, 1); | ||
//=> 4 | ||
grid.getValue(1, 1); //=> 4 | ||
grid.toArrays(); //=> [ [1, 2], [3, 4, 5] ] | ||
grid.toArrays(); | ||
//=> [ [1, 2], [3, 4, 5] ] | ||
// you can choose to keep the padding values | ||
grid.toArrays(true); | ||
//=> [ [1, 2, 0, 0], [3, 4, 5, 0] ] | ||
grid.toArrays(true); //=> [ [1, 2, 0, 0], [3, 4, 5, 0] ] | ||
``` | ||
@@ -971,7 +881,5 @@ | ||
const grid = ArrayGrid.create(100, 100); | ||
grid.length; | ||
//=> 12800 | ||
grid.length; //=> 12800 | ||
const symmetricGrid = SymmetricGrid.create(100); | ||
symmetricGrid.length; | ||
//=> 5050 | ||
symmetricGrid.length; //=> 5050 | ||
``` | ||
@@ -984,6 +892,4 @@ | ||
symmetricGrid.setValue(0, 5, 10); | ||
symmetricGrid.getValue(0, 5); | ||
//=> 10 | ||
symmetricGrid.getValue(5, 0); | ||
//=> 10 | ||
symmetricGrid.getValue(0, 5); //=> 10 | ||
symmetricGrid.getValue(5, 0); //=> 10 | ||
``` | ||
@@ -1012,15 +918,12 @@ | ||
const heap = new BinaryHeap(10, 1, 20, 3, 9, 8); | ||
heap[0]; | ||
//=> 1 | ||
heap.left(0); // the left child of the first (minimal) element of the heap | ||
//=> 3 | ||
heap.right(0); // the right child of the first (minimal) element of the heap | ||
//=> 8 | ||
heap.parent(1); // the parent of the second element of the heap | ||
//=> 1 | ||
heap.replace(4); // returns the first element and adds a new element in one operation | ||
//=> 1 | ||
heap[0]; | ||
//=> 3 | ||
heap[0]; //=> 1 | ||
// the left child of the first (minimal) element of the heap | ||
heap.left(0); //=> 3 | ||
// the right child of the first (minimal) element of the heap | ||
heap.right(0); //=> 8 | ||
// the parent of the second element of the heap | ||
heap.parent(1); //=> 1 | ||
// returns the first element and adds a new element in one operation | ||
heap.replace(4); //=> 1 | ||
heap[0]; //=> 3 | ||
heap[0] = 6; | ||
@@ -1064,10 +967,6 @@ // BinaryHeap [ 6, 4, 8, 10, 9, 20 ] | ||
a.unique = true; | ||
a.push(1); | ||
//=> 1 | ||
a.push(2); | ||
//=> 2 | ||
a.push(1); | ||
//=> 2 | ||
a; | ||
//=> SortedArray [ 1, 2 ] | ||
a.push(1); //=> 1 | ||
a.push(2); //=> 2 | ||
a.push(1); //=> 2 | ||
a; //=> SortedArray [ 1, 2 ] | ||
``` | ||
@@ -1074,0 +973,0 @@ |
@@ -83,2 +83,10 @@ import type { IndexedCollection } from "./utility-types"; | ||
/** | ||
* Checks whether the provided encoded sequence is found inside the view. | ||
* | ||
* @param searchValue the value to search for | ||
* @param position the starting position | ||
* @return whether the value is found | ||
*/ | ||
includes(searchValue: IndexedCollection, position?: number): boolean; | ||
/** | ||
* Returns the index within the StringView | ||
@@ -92,3 +100,3 @@ * of the first occurrence of the specified value, starting the search at start. | ||
*/ | ||
search(searchValue: IndexedCollection, fromIndex?: number): number; | ||
indexOf(searchValue: IndexedCollection, fromIndex?: number): number; | ||
searchNaive(searchValue: IndexedCollection, start: number): number; | ||
@@ -95,0 +103,0 @@ searchShiftOr(searchValue: IndexedCollection, start: number): number; |
@@ -251,3 +251,3 @@ export class StringView extends DataView { | ||
while (position < this.byteLength) { | ||
const currentIndex = this.search(pattern, position); | ||
const currentIndex = this.indexOf(pattern, position); | ||
if (!~currentIndex) | ||
@@ -294,2 +294,12 @@ break; | ||
/** | ||
* Checks whether the provided encoded sequence is found inside the view. | ||
* | ||
* @param searchValue the value to search for | ||
* @param position the starting position | ||
* @return whether the value is found | ||
*/ | ||
includes(searchValue, position) { | ||
return this.indexOf(searchValue, position) !== -1; | ||
} | ||
/** | ||
* Returns the index within the StringView | ||
@@ -303,3 +313,3 @@ * of the first occurrence of the specified value, starting the search at start. | ||
*/ | ||
search(searchValue, fromIndex = 0) { | ||
indexOf(searchValue, fromIndex = 0) { | ||
if (this.byteLength > 256 && searchValue.length < 32) { | ||
@@ -306,0 +316,0 @@ return this.searchShiftOr(searchValue, fromIndex); |
@@ -13,2 +13,3 @@ import type { ComplexView, ContainerView, PrimitiveView, ViewConstructor, ViewInstance } from "./view-types"; | ||
[Symbol.iterator](): Generator<ViewInstance<T> | undefined, void, unknown>; | ||
at(index: number): T | undefined; | ||
get(index: number): T | undefined; | ||
@@ -15,0 +16,0 @@ getLength(index: number): number; |
@@ -77,2 +77,7 @@ export class VectorView extends DataView { | ||
} | ||
at(index) { | ||
if (index < 0) | ||
return this.get(this.size + index); | ||
return this.get(index); | ||
} | ||
get(index) { | ||
@@ -79,0 +84,0 @@ const View = this.constructor |
@@ -25,2 +25,8 @@ import { Constructor } from "./utility-types"; | ||
* | ||
* @param index the of the item. | ||
*/ | ||
at(index: number): T | undefined; | ||
/** | ||
* Get the JavaScript value of an item. | ||
* | ||
* @param index the index of the item | ||
@@ -168,3 +174,3 @@ * @return the item | ||
$id?: string; | ||
$ref?: string; | ||
$ref?: `#${string}`; | ||
maxLength?: number; | ||
@@ -171,0 +177,0 @@ minLength?: number; |
@@ -21,3 +21,3 @@ import type { ComplexView, ContainerView, PrimitiveView, ViewConstructor, ViewFieldLayout, ViewInstance, ViewLayout, ViewSchema } from "./view-types"; | ||
static get maxView(): DataView; | ||
static create<T>(schema: ViewSchema<T>, constructor?: Constructor<T extends object ? T : never>): ViewConstructor<T>; | ||
static create<T>(schema: ViewSchema<T>, constructor?: T extends object ? Constructor<T> : never): ViewConstructor<T>; | ||
static view<T>(view: DataView): ViewInstance<T> | undefined; | ||
@@ -24,0 +24,0 @@ static decode<T>(view: DataView): T | undefined; |
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
Sorry, the diff of this file is not supported yet
533335
6820
982