Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
42 changes: 19 additions & 23 deletions src/bundles/binary_tree/src/__tests__/index.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,18 +3,14 @@ import { TestDataHandler, emptyListValue, numberValue } from '@sourceacademy/mod
import { describe, expect, it } from 'vitest';
import * as funcs from '../functions';

async function opaqueNumber(handler: TestDataHandler, value: number) {
return handler.opaque_make(value);
}

async function rawTree(
handler: TestDataHandler,
value: number,
left: TypedValue<DataType>,
right: TypedValue<DataType>
) {
return handler.pair_make(
await opaqueNumber(handler, value),
numberValue(value),
await handler.pair_make(left, await handler.pair_make(right, emptyListValue()))
);
}
Expand Down Expand Up @@ -57,7 +53,7 @@ describe(funcs.is_tree, () => {
const rightLeaf = await rawTree(handler, 1, emptyListValue(), emptyListValue());
const rightSubtree = await handler.pair_make(rightLeaf, emptyListValue());
const tree = await handler.pair_make(
await opaqueNumber(handler, 0),
numberValue(0),
await handler.pair_make(leftLeaf, rightSubtree)
);
await expect(funcs.is_tree(handler, tree)).resolves.toEqual(true);
Expand All @@ -76,26 +72,26 @@ describe(funcs.is_tree, () => {
await handler.array_set(leftPair, 0, emptyListValue());
await handler.array_set(leftPair, 1, rightPair);
const tree = await handler.array_make(DataType.ANY, 2, emptyListValue());
await handler.array_set(tree, 0, await opaqueNumber(handler, 0));
await handler.array_set(tree, 0, numberValue(0));
await handler.array_set(tree, 1, leftPair);

await expect(funcs.is_tree(handler, tree)).resolves.toEqual(true);
await expect(handler.opaque_get(await funcs.entry(handler, tree))).resolves.toEqual(0);
expect(await funcs.entry(handler, tree)).toEqual(numberValue(0));
});
});

describe(funcs.make_tree, () => {
it('throws when left is not a tree', async () => {
const handler = new TestDataHandler();
await expect(
funcs.make_tree(handler, await opaqueNumber(handler, 0), numberValue(0) as unknown as TypedValue<DataType.LIST>, funcs.make_empty_tree())
funcs.make_tree(handler, numberValue(0), numberValue(0) as unknown as TypedValue<DataType.LIST>, funcs.make_empty_tree())
).rejects.toThrowError('make_tree expects binary tree for left');
});

it('throws when right is not a tree', async () => {
const handler = new TestDataHandler();
await expect(
funcs.make_tree(handler, await opaqueNumber(handler, 0), funcs.make_empty_tree(), numberValue(0) as unknown as TypedValue<DataType.LIST>)
funcs.make_tree(handler, numberValue(0), funcs.make_empty_tree(), numberValue(0) as unknown as TypedValue<DataType.LIST>)
).rejects.toThrowError('make_tree expects binary tree for right');
});
});
Expand All @@ -117,12 +113,12 @@ describe(funcs.entry, () => {
const handler = new TestDataHandler();
const tree = await funcs.make_tree(
handler,
await opaqueNumber(handler, 0),
numberValue(0),
funcs.make_empty_tree(),
funcs.make_empty_tree()
);
const result = await funcs.entry(handler, tree);
await expect(handler.opaque_get(result)).resolves.toEqual(0);
expect(result).toEqual(numberValue(0));
});
});

Expand All @@ -143,7 +139,7 @@ describe(funcs.left_branch, () => {
const handler = new TestDataHandler();
const tree = await funcs.make_tree(
handler,
await opaqueNumber(handler, 0),
numberValue(0),
funcs.make_empty_tree(),
funcs.make_empty_tree()
);
Expand All @@ -155,21 +151,21 @@ describe(funcs.left_branch, () => {
const handler = new TestDataHandler();
const innerTree = await funcs.make_tree(
handler,
await opaqueNumber(handler, 1),
numberValue(1),
funcs.make_empty_tree(),
funcs.make_empty_tree()
);
const tree = await funcs.make_tree(
handler,
await opaqueNumber(handler, 0),
numberValue(0),
innerTree,
funcs.make_empty_tree()
);

await expect(handler.opaque_get(await funcs.entry(handler, tree))).resolves.toEqual(0);
expect(await funcs.entry(handler, tree)).toEqual(numberValue(0));

const leftTree = await funcs.left_branch(handler, tree);
await expect(handler.opaque_get(await funcs.entry(handler, leftTree))).resolves.toEqual(1);
expect(await funcs.entry(handler, leftTree)).toEqual(numberValue(1));
});
});

Expand All @@ -192,7 +188,7 @@ describe(funcs.right_branch, () => {
const handler = new TestDataHandler();
const tree = await funcs.make_tree(
handler,
await opaqueNumber(handler, 0),
numberValue(0),
funcs.make_empty_tree(),
funcs.make_empty_tree()
);
Expand All @@ -204,21 +200,21 @@ describe(funcs.right_branch, () => {
const handler = new TestDataHandler();
const leftTree = await funcs.make_tree(
handler,
await opaqueNumber(handler, 1),
numberValue(1),
funcs.make_empty_tree(),
funcs.make_empty_tree()
);
const rightTree = await funcs.make_tree(
handler,
await opaqueNumber(handler, 2),
numberValue(2),
funcs.make_empty_tree(),
funcs.make_empty_tree()
);
const tree = await funcs.make_tree(handler, await opaqueNumber(handler, 0), leftTree, rightTree);
const tree = await funcs.make_tree(handler, numberValue(0), leftTree, rightTree);

await expect(handler.opaque_get(await funcs.entry(handler, tree))).resolves.toEqual(0);
expect(await funcs.entry(handler, tree)).toEqual(numberValue(0));

const right = await funcs.right_branch(handler, tree);
await expect(handler.opaque_get(await funcs.entry(handler, right))).resolves.toEqual(2);
expect(await funcs.entry(handler, right)).toEqual(numberValue(2));
});
});
6 changes: 3 additions & 3 deletions src/bundles/binary_tree/src/functions.ts
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ export function make_empty_tree(): EmptyBinaryTree {
*/
export async function make_tree(
evaluator: IDataHandler,
value: TypedValue<DataType.OPAQUE>,
value: TypedValue<DataType>,
left: BinaryTree,
right: BinaryTree
): Promise<NonEmptyBinaryTree> {
Expand Down Expand Up @@ -136,9 +136,9 @@ async function assertNonEmptyTree(
* @param t BinaryTree to be accessed
* @returns Value
*/
export async function entry(evaluator: IDataHandler, t: TypedValue<DataType>): Promise<TypedValue<DataType.OPAQUE>> {
export async function entry(evaluator: IDataHandler, t: TypedValue<DataType>): Promise<TypedValue<DataType>> {
const tree = await assertNonEmptyTree(evaluator, t, entry.name);
return (await evaluator.pair_head(tree)) as TypedValue<DataType.OPAQUE>;
return evaluator.pair_head(tree);
}

/**
Expand Down
10 changes: 6 additions & 4 deletions src/bundles/binary_tree/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -40,9 +40,11 @@ export default class BinaryTreeModulePlugin extends BaseModulePlugin {
return make_empty_tree_func();
}

@moduleMethod([DataType.OPAQUE, DataType.LIST, DataType.LIST], DataType.PAIR)
// The entry is DataType.ANY, not OPAQUE: it may be any value, and a number or string is not an
// OPAQUE handle.
@moduleMethod([DataType.ANY, DataType.LIST, DataType.LIST], DataType.PAIR)
async* make_tree(
value: TypedValue<DataType.OPAQUE>,
value: TypedValue<DataType.ANY>,
left: TypedValue<DataType.LIST>,
right: TypedValue<DataType.LIST>
): AsyncGenerator<void, TypedValue<DataType.PAIR>, unknown> {
Expand All @@ -64,8 +66,8 @@ export default class BinaryTreeModulePlugin extends BaseModulePlugin {
return { type: DataType.BOOLEAN, value: is_empty_tree_func(value) };
}

@moduleMethod([DataType.LIST], DataType.OPAQUE)
async* entry(t: TypedValue<DataType.LIST>): AsyncGenerator<void, TypedValue<DataType.OPAQUE>, unknown> {
@moduleMethod([DataType.LIST], DataType.ANY)
async* entry(t: TypedValue<DataType.LIST>): AsyncGenerator<void, TypedValue<DataType.ANY>, unknown> {
return await entry_func(this.evaluator, t);
}

Expand Down
Loading