Skip to content

Commit

Permalink
Merge branch 'master' into ex-4-33-sol
Browse files Browse the repository at this point in the history
  • Loading branch information
RichDom2185 authored Jul 10, 2024
2 parents dcca666 + 6f7425c commit bbd5588
Show file tree
Hide file tree
Showing 17 changed files with 1,067 additions and 643 deletions.
6 changes: 3 additions & 3 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -25,9 +25,9 @@
},
"homepage": "https://sourceacademy.org/sicpjs",
"devDependencies": {
"@babel/node": "^7.24.6",
"@babel/core": "^7.24.6",
"@babel/preset-env": "^7.24.6",
"@babel/node": "^7.24.7",
"@babel/core": "^7.24.7",
"@babel/preset-env": "^7.24.7",
"fs-extra": "^11.2.0",
"http-server": "^14.1.1",
"husky": "^8.0.3",
Expand Down
Binary file added static/img_javascript/ex-3-13-sol.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added static/img_javascript/ex-3-14-sol-1.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added static/img_javascript/ex-3-14-sol-2.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added static/img_javascript/ex5-1-solution-1.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added static/img_javascript/ex5-1-solution-2.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
12 changes: 8 additions & 4 deletions xml/chapter1/section1/subsection6.xml
Original file line number Diff line number Diff line change
Expand Up @@ -231,7 +231,9 @@ abs(-5);
<META>alternative-expression</META> and returns its value as the value of the
conditional.<FOOTNOTE>
<INDEX>conditional expression<SUBINDEX>non-boolean value as predicate</SUBINDEX></INDEX>
Conditionals in full JavaScript accept any value, not just a boolean, as the result of evaluating
Conditionals
<LABEL NAME="foot:any-value-as-predicate"/>
in full JavaScript accept any value, not just a boolean, as the result of evaluating
the <META>predicate</META> expression (see footnote<SPACE/><REF NAME="foot:truthy"/>
in section<SPACE/><REF NAME="sec:eval-data-structures"/> for details). The programs in this book
use only boolean values as predicates of conditionals.
Expand Down Expand Up @@ -591,8 +593,10 @@ $\vdots$
<INDEX>evaluation<SUBINDEX>of <JAVASCRIPTINLINE>&amp;&amp;</JAVASCRIPTINLINE><ORDER>of ;1</ORDER></SUBINDEX><FRAGILE/></INDEX>
<EM>logical conjunction</EM>, meaning roughly
the same as the English word <QUOTE>and.</QUOTE>
This syntactic form is syntactic sugar<FOOTNOTE>
Syntactic forms that are simply convenient
We assume<FOOTNOTE>This assumption is justified by the restriction mentioned
in footnote<SPACE/><REF NAME="foot:any-value-as-predicate"/>. Full JavaScript
needs to consider the case where the result of evaluating <META>expression</META><LATEXINLINE>$_1$</LATEXINLINE> is neither true nor false.</FOOTNOTE> this syntactic form to be syntactic
sugar<FOOTNOTE>Syntactic forms that are simply convenient
alternative surface structures for things that can be written in more
uniform ways are sometimes called <EM>syntactic sugar</EM>, to use a
phrase coined by
Expand All @@ -617,7 +621,7 @@ $\vdots$
<INDEX>evaluation<SUBINDEX>of {\tt "|"|}<ORDER>of ;2</ORDER></SUBINDEX><FRAGILE/></INDEX>
<EM>logical disjunction</EM>, meaning roughly
the same as the English word <QUOTE>or.</QUOTE>
This syntactic form is syntactic sugar for<BR/>
We assume this syntactic form to be syntactic sugar for<BR/>
<META>expression</META><LATEXINLINE>$_1$</LATEXINLINE> <JAVASCRIPTINLINE>?</JAVASCRIPTINLINE>
<JAVASCRIPTINLINE>true</JAVASCRIPTINLINE> <JAVASCRIPTINLINE>:</JAVASCRIPTINLINE>
<META>expression</META><LATEXINLINE>$_2$</LATEXINLINE>.
Expand Down
2 changes: 1 addition & 1 deletion xml/chapter2/section2/subsection3.xml
Original file line number Diff line number Diff line change
Expand Up @@ -1451,7 +1451,7 @@ function matrix_times_vector(m, v) {
function transpose(mat) {
return accumulate_n(<METAPHRASE>??</METAPHRASE>, <METAPHRASE>??</METAPHRASE>, mat);
}
function matrix_times_matrix(n, m) {
function matrix_times_matrix(m, n) {
const cols = transpose(n);
return map(<METAPHRASE>??</METAPHRASE>, m);
}
Expand Down
48 changes: 48 additions & 0 deletions xml/chapter2/section5/subsection1.xml
Original file line number Diff line number Diff line change
Expand Up @@ -994,6 +994,54 @@ function install_complex_package() {
arithmetic package. This operation should work for ordinary numbers,
rational numbers, and complex numbers.
<LABEL NAME="ex:=zero?"/>
<SOLUTION>
<SNIPPET EVAL="no">
<JAVASCRIPT>
// provided by GitHub user clean99

function is_equal_to_zero(x) {
return apply_generic("is_equal", list(x));
}

function install_javascript_number_package() {
// ...

put("is_equal_to_zero", "javascript_number",
x => x === 0);

// ...
}

function install_rational_package() {
// ...

function is_equal_to_zero(x) {
return numer(x) === 0;
}

put("is_equal_to_zero", "rational",
is_equal_to_zero);

// ...
}

function install_complex_package() {
// ...

function is_equal_to_zero(z) {
return real_part(z) === 0
? imag_part(z) === 0
: false;
}

put("is_equal_to_zero", "complex",
is_equal_to_zero);

//...
}
</JAVASCRIPT>
</SNIPPET>
</SOLUTION>
</EXERCISE>

<INDEX>generic arithmetic operations<CLOSE/></INDEX>
Expand Down
132 changes: 132 additions & 0 deletions xml/chapter3/section3/subsection1.xml
Original file line number Diff line number Diff line change
Expand Up @@ -832,6 +832,17 @@ list_ref(z, 100);
</JAVASCRIPT>
</SPLITINLINE>
<LABEL NAME="ex:make-cycle"/>
<SOLUTION>
(provided by GitHub user jonathantorres)
If we try to compute <JAVASCRIPTINLINE>last_pair(z)</JAVASCRIPTINLINE>, the
program will enter in a infinite loop, since the end of the list points back
to the beginning.

<FIGURE src="img_javascript/ex-3-13-sol.png">
<LABEL NAME= "ex:3-13-sol"/>
</FIGURE>

</SOLUTION>
</EXERCISE>

<EXERCISE>
Expand Down Expand Up @@ -934,6 +945,33 @@ const w = mystery(v);
What would be printed as the values of <SCHEMEINLINE>v</SCHEMEINLINE>
and <SCHEMEINLINE>w</SCHEMEINLINE>?
<LABEL NAME="ex:mystery"/>
<SOLUTION>
(provided by GitHub user jonathantorres)
The application <JAVASCRIPTINLINE>mystery(x)</JAVASCRIPTINLINE> will
reverse the list <JAVASCRIPTINLINE>x</JAVASCRIPTINLINE> in-place.
Initially
<JAVASCRIPTINLINE>v</JAVASCRIPTINLINE> looks like this:

<FIGURE src="img_javascript/ex-3-14-sol-2.png">
<LABEL NAME= "ex:3-14-sol-1"/>
</FIGURE>

After evaluating
<JAVASCRIPTINLINE>const w = mystery(v);</JAVASCRIPTINLINE>
the values of
<JAVASCRIPTINLINE>v</JAVASCRIPTINLINE> and
<JAVASCRIPTINLINE>w</JAVASCRIPTINLINE> become:

<FIGURE src="img_javascript/ex-3-14-sol-2.png">
<LABEL NAME= "ex:3-14-sol-2"/>
</FIGURE>

The function <JAVASCRIPTINLINE>display</JAVASCRIPTINLINE>
prints <JAVASCRIPTINLINE>["a", null]</JAVASCRIPTINLINE> for
<JAVASCRIPTINLINE>v</JAVASCRIPTINLINE> and
<JAVASCRIPTINLINE>["d", ["c", ["b", ["a", null]]]]</JAVASCRIPTINLINE> for
<JAVASCRIPTINLINE>w</JAVASCRIPTINLINE>.
</SOLUTION>
</EXERCISE>

<INDEX>mutable data objects<SUBINDEX>list structure<CLOSE/></SUBINDEX></INDEX>
Expand Down Expand Up @@ -1522,6 +1560,56 @@ display(count_pairs(cycle));
distinct pairs in any structure. (Hint: Traverse the structure, maintaining
an auxiliary data structure that is used to keep track of which pairs have
already been counted.)
<SOLUTION>
<SNIPPET>
<EXAMPLE>exercise_3_17_solution_example</EXAMPLE>
<JAVASCRIPT>
// solution provided by GitHub user clean99

function count_pairs(x) {
let counted_pairs = null;
function is_counted_pair(current_counted_pairs, x) {
return is_null(current_counted_pairs)
? false
: head(current_counted_pairs) === x
? true
: is_counted_pair(tail(current_counted_pairs), x);
}
function count(x) {
if(! is_pair(x) || is_counted_pair(counted_pairs, x)) {
return 0;
} else {
counted_pairs = pair(x, counted_pairs);
return count(head(x)) +
count(tail(x)) +
1;
}
}
return count(x);
}
</JAVASCRIPT>
</SNIPPET>
<SNIPPET HIDE="yes">
<NAME>exercise_3_17_solution_example</NAME>
<JAVASCRIPT>
const three_list = list("a", "b", "c");
const one = pair("d", "e");
const two = pair(one, one);
const four_list = pair(two, "f");
const seven_list = pair(two, two);
const cycle = list("g", "h", "i");
set_tail(tail(tail(cycle)), cycle);

// return 3; return 3; return 3;
display(count_pairs(three_list));
display(count_pairs(four_list));
display(count_pairs(seven_list));

// return 3
display(count_pairs(cycle));
</JAVASCRIPT>
</SNIPPET>
</SOLUTION>
</EXERCISE>

<EXERCISE>
Expand All @@ -1542,6 +1630,50 @@ display(count_pairs(cycle));
would go into an infinite loop. Exercise<SPACE/><REF NAME="ex:make-cycle"/>
constructed such lists.
<LABEL NAME="ex:find-cycle"/>
<SOLUTION>
<SNIPPET>
<EXAMPLE>exercise_3_18_solution_example</EXAMPLE>
<JAVASCRIPT>
// solution provided by GitHub user clean99

function contains_cycle(x) {
let counted_pairs = null;
function is_counted_pair(counted_pairs, x) {
return is_null(counted_pairs)
? false
: head(counted_pairs) === x
? true
: is_counted_pair(tail(counted_pairs), x);
}
function detect_cycle(x) {
if (is_null(x)) {
return false;
} else if (is_counted_pair(counted_pairs, x)) {
return true;
} else {
counted_pairs = pair(x, counted_pairs);
return detect_cycle(tail(x));
}
}
return detect_cycle(x);
}
</JAVASCRIPT>
</SNIPPET>
<SNIPPET HIDE="yes">
<NAME>exercise_3_18_solution_example</NAME>
<JAVASCRIPT>
const three_list = list("a", "b", "c");
const cycle = list("g", "h", "i");
set_tail(tail(tail(cycle)), cycle);

// displays false
display(contains_cycle(three_list));

// displays true
display(contains_cycle(cycle));
</JAVASCRIPT>
</SNIPPET>
</SOLUTION>
</EXERCISE>

<EXERCISE>
Expand Down
92 changes: 92 additions & 0 deletions xml/chapter3/section3/subsection2.xml
Original file line number Diff line number Diff line change
Expand Up @@ -951,6 +951,98 @@ print_queue(q); // prints: ["b", null]
All operations should be accomplished in
<LATEXINLINE>$\Theta(1)$</LATEXINLINE> steps.
<LABEL NAME="ex:deque"/>
<SOLUTION>
<SNIPPET>
<JAVASCRIPT>
// solution provided by GitHub user clean99
function make_deque() {
return pair(null, null);
}

function front_ptr(deque) {
return head(deque);
}

function rear_ptr(deque) {
return tail(deque);
}

function set_front_ptr(deque, item) {
set_head(deque, item);
}

function set_rear_ptr(deque, item) {
set_tail(deque, item);
}

function is_empty_deque(deque) {
return is_null(front_ptr(deque))
? true
: is_null(rear_ptr(deque))
? true
: false;
}

function is_one_item_deque(deque) {
return front_ptr(deque) === rear_ptr(deque);
}

function front_insert_deque(deque, item) {
// use another pair to store a forward pointer
const new_pair = pair(pair(item, null), null);
if (is_empty_deque(deque)) {
set_front_ptr(deque, new_pair);
set_rear_ptr(deque, new_pair);
} else {
set_tail(new_pair, front_ptr(deque));
// set forward pointer to new_pair
set_tail(head(front_ptr(deque)), new_pair);
set_front_ptr(deque, new_pair);
}
}

function front_delete_deque(deque) {
if (is_empty_deque(deque)) {
error(deque, "front_delete_deque called with an empty deque");
} else if(is_one_item_deque(deque)) {
set_front_ptr(deque, null);
set_rear_ptr(deque, null);
return deque;
} else {
set_front_ptr(deque, tail(front_ptr(deque)));
return deque;
}
}

function rear_insert_deque(deque, item) {
if (is_empty_deque(deque)) {
const new_pair = pair(pair(item, null), null);
set_front_ptr(deque, new_pair);
set_rear_ptr(deque, new_pair);
} else {
// set new_pair forward pointer to last item
const new_pair = pair(pair(item, rear_ptr(deque)), null);
set_tail(rear_ptr(deque), new_pair);
set_rear_ptr(deque, new_pair);
}
}

function rear_delete_deque(deque) {
if (is_empty_deque(deque)) {
error(deque, "rear_delete_deque called with an empty deque");
} else if(is_one_item_deque(deque)) {
set_front_ptr(deque, null);
set_rear_ptr(deque, null);
return deque;
} else {
// update rear_ptr to last item's forward pointer
set_rear_ptr(deque, tail(head(rear_ptr(deque))));
return deque;
}
}
</JAVASCRIPT>
</SNIPPET>
</SOLUTION>
</EXERCISE>
<INDEX>queue<CLOSE/></INDEX>
</SUBSECTION>
Loading

0 comments on commit bbd5588

Please sign in to comment.