2016 Update

This commit is contained in:
Tina Müller 2016-12-05 22:15:40 +01:00
parent 948b86eafa
commit dcf5d15da3
7965 changed files with 139854 additions and 31002 deletions

View file

@ -1,19 +1,27 @@
These two sequences of positive integers are defined as:
:<math>\begin{align}
:::: <big><math>\begin{align}
R(1)&=1\ ;\ S(1)=2 \\
R(n)&=R(n-1)+S(n-1), \quad n>1.
\end{align}</math>
:The sequence <math>S(n)</math> is further defined as the sequence of positive integers ''not'' present in <math>R(n)</math>.
Sequence R starts: 1, 3, 7, 12, 18, ...<br>
Sequence S starts: 2, 4, 5, 6, 8, ...
\end{align}</math></big>
<br>
The sequence <big><math>S(n)</math></big> is further defined as the sequence of positive integers '''''not''''' present in <big><math>R(n)</math></big>.
Sequence <big><math>R</math></big> starts:
1, 3, 7, 12, 18, ...
Sequence <big><math>S</math></big> starts:
2, 4, 5, 6, 8, ...
;Task:
# Create two functions named '''ffr''' and '''ffs''' that when given '''n''' return '''R(n)''' or '''S(n)''' respectively.<br>(Note that R(1) = 1 and S(1) = 2 to avoid off-by-one errors).
# No maximum value for '''n''' should be assumed.
# Calculate and show that the first ten values of '''R''' are:<br> 1, 3, 7, 12, 18, 26, 35, 45, 56, and 69
# Calculate and show that the first 40 values of '''ffr''' plus the first 960 values of '''ffs''' include all the integers from 1 to 1000 exactly once.
Task:
# Create two functions named ffr and ffs that when given n return R(n) or S(n) respectively.<br><small>(Note that R(1) = 1 and S(1) = 2 to avoid off-by-one errors).</small>
# No maximum value for n should be assumed.
# Calculate and show that the first ten values of R are: 1, 3, 7, 12, 18, 26, 35, 45, 56, and 69
# Calculate and show that the first 40 values of ffr plus the first 960 values of ffs include all the integers from 1 to 1000 exactly once.
;References:
* Sloane's [http://oeis.org/A005228 A005228] and [http://oeis.org/A030124 A030124].
* [http://mathworld.wolfram.com/HofstadterFigure-FigureSequence.html Wolfram Mathworld]
* [http://mathworld.wolfram.com/HofstadterFigure-FigureSequence.html Wolfram MathWorld]
* Wikipedia: [[wp:Hofstadter_sequence#Hofstadter_Figure-Figure_sequences|Hofstadter Figure-Figure sequences]].
<br><br>

View file

@ -0,0 +1,66 @@
#include <iomanip>
#include <iostream>
#include <set>
#include <vector>
using namespace std;
unsigned hofstadter(unsigned rlistSize, unsigned slistSize)
{
auto n = rlistSize > slistSize ? rlistSize : slistSize;
auto rlist = new vector<unsigned> { 1, 3, 7 };
auto slist = new vector<unsigned> { 2, 4, 5, 6 };
auto list = rlistSize > 0 ? rlist : slist;
auto target_size = rlistSize > 0 ? rlistSize : slistSize;
while (list->size() > target_size) list->pop_back();
while (list->size() < target_size)
{
auto lastIndex = rlist->size() - 1;
auto lastr = (*rlist)[lastIndex];
auto r = lastr + (*slist)[lastIndex];
rlist->push_back(r);
for (auto s = lastr + 1; s < r && list->size() < target_size;)
slist->push_back(s++);
}
auto v = (*list)[n - 1];
delete rlist;
delete slist;
return v;
}
ostream& operator<<(ostream& os, const set<unsigned>& s)
{
cout << '(' << s.size() << "):";
auto i = 0;
for (auto c = s.begin(); c != s.end();)
{
if (i++ % 20 == 0) os << endl;
os << setw(5) << *c++;
}
return os;
}
int main(int argc, const char* argv[])
{
const auto v1 = atoi(argv[1]);
const auto v2 = atoi(argv[2]);
set<unsigned> r, s;
for (auto n = 1; n <= v2; n++)
{
if (n <= v1)
r.insert(hofstadter(n, 0));
s.insert(hofstadter(0, n));
}
cout << "R" << r << endl;
cout << "S" << s << endl;
int m = max(*r.rbegin(), *s.rbegin());
for (auto n = 1; n <= m; n++)
if (r.count(n) == s.count(n))
clog << "integer " << n << " either in both or neither set" << endl;
return 0;
}

View file

@ -0,0 +1,10 @@
% ./hofstadter 40 100 2> /dev/null
R(40):
1 3 7 12 18 26 35 45 56 69 83 98 114 131 150 170 191 213 236 260
285 312 340 369 399 430 462 495 529 565 602 640 679 719 760 802 845 889 935 982
S(100):
2 4 5 6 8 9 10 11 13 14 15 16 17 19 20 21 22 23 24 25
27 28 29 30 31 32 33 34 36 37 38 39 40 41 42 43 44 46 47 48
49 50 51 52 53 54 55 57 58 59 60 61 62 63 64 65 66 67 68 70
71 72 73 74 75 76 77 78 79 80 81 82 84 85 86 87 88 89 90 91
92 93 94 95 96 97 99 100 101 102 103 104 105 106 107 108 109 110 111 112

View file

@ -0,0 +1,26 @@
R = [ null, 1 ]
S = [ null, 2 ]
extend_sequences = (n) ->
current = Math.max(R[R.length - 1], S[S.length - 1])
i = undefined
while R.length <= n or S.length <= n
i = Math.min(R.length, S.length) - 1
current += 1
if current == R[i] + S[i]
R.push current
else
S.push current
ff = (X, n) ->
extend_sequences n
X[n]
console.log 'R(' + i + ') = ' + ff(R, i) for i in [1..10]
int_array = ([1..40].map (i) -> ff(R, i)).concat [1..960].map (i) -> ff(S, i)
int_array.sort (a, b) -> a - b
for i in [1..1000]
if int_array[i - 1] != i
throw 'Something\'s wrong!'
console.log '1000 integer check ok.'

View file

@ -0,0 +1,34 @@
;;; equally doable with a list
(flet ((seq (i) (make-array 1 :element-type 'integer
:initial-element i
:fill-pointer 1
:adjustable t)))
(let ((rr (seq 1)) (ss (seq 2)))
(labels ((extend-r ()
(let* ((l (1- (length rr)))
(r (+ (aref rr l) (aref ss l)))
(s (elt ss (1- (length ss)))))
(vector-push-extend r rr)
(loop while (<= s r) do
(if (/= (incf s) r)
(vector-push-extend s ss))))))
(defun seq-r (n)
(loop while (> n (length rr)) do (extend-r))
(elt rr (1- n)))
(defun seq-s (n)
(loop while (> n (length ss)) do (extend-r))
(elt ss (1- n))))))
(defun take (f n)
(loop for x from 1 to n collect (funcall f x)))
(format t "First of R: ~a~%" (take #'seq-r 10))
(mapl (lambda (l) (if (and (cdr l)
(/= (1+ (car l)) (cadr l)))
(error "not in sequence")))
(sort (append (take #'seq-r 40)
(take #'seq-s 960))
#'<))
(princ "Ok")

View file

@ -1,43 +1,43 @@
/*REXX program calculates and verifies the Hofstadter Figure─Figure sequences.*/
parse arg x top bot . /*obtain optional arguments from the CL*/
if x=='' | x==',' then x= 10 /*Not specified? Then use the default.*/
if top=='' | top==',' then top=1000 /* " " " " " " */
if bot=='' | bot==',' then bot= 40 /* " " " " " " */
low=1; if x<0 then low=abs(x) /*only display a single │X│ value? */
r.=0; r.1=1; rr.=r.; rr.1=1; s.=r.; s.1=2 /*initialize the R RR S arrays.*/
errs=0; $.=0
do i=low to abs(x) /*display the 1st X values of R & S.*/
say right('R('i") =", 20) right(ffr(i), 7),
right('S('i") =", 20) right(ffs(i), 7)
end /*i*/
if x<1 then exit
do m=1 for bot; r=ffr(m); $.r=1
end /*m*/ /* [↑] calculate the 1st 40 R values.*/
do n=1 for top-bot; s=ffs(n)
if $.s then call ser 'duplicate number in R and S lists:' s; $.s=1
end /*n*/ /* [↑] calculate the 1st 960 S values.*/
do v=1 for top
if \$.v then call ser 'missing R S:' v
end /*v*/ /* [↑] are all 1≤ numbers ≤1k present?*/
/*REXX program calculates and verifies the Hofstadter Figure─Figure sequences. */
parse arg x top bot . /*obtain optional arguments from the CL*/
if x=='' | x=="," then x= 10 /*Not specified? Then use the default.*/
if top=='' | top=="," then top=1000 /* " " " " " " */
if bot=='' | bot=="," then bot= 40 /* " " " " " " */
low=1; if x<0 then low=abs(x) /*only display a single │X│ value? */
r.=0; r.1=1; rr.=r.; rr.1=1; s.=r.; s.1=2 /*initialize the R, RR, and S arrays.*/
errs=0 /*the number of errors found (so far).*/
do i=low to abs(x) /*display the 1st X values of R & S.*/
say right('R('i") =",20) right(FFR(i),7) right('S('i") =",20) right(FFS(i),7)
end /*i*/
/* [↑] list the 1st X Fig─Fig numbers.*/
if x<1 then exit /*if X isn't positive, then we're done.*/
$.=0 /*initialize the memoization ($) array.*/
do m=1 for bot; r=FFR(m); $.r=1 /*calculate the first forty R values.*/
end /*m*/ /* [↑] ($.) is used for memoization. */
/* [↓] check for duplicate #s in R & S*/
do n=1 for top-bot; s=FFS(n) /*calculate the value of FFS(n). */
if $.s then call ser 'duplicate number in R and S lists:' s; $.s=1
end /*n*/ /* [↑] calculate the 1st 960 S values.*/
/* [↓] check for missing values in R│S*/
do v=1 for top; if \$.v then call ser 'missing R S:' v
end /*v*/ /* [↑] are all 1≤ numbers ≤1k present?*/
say
if errs==0 then say 'verification completed for all numbers from 1 ' top " [inclusive]."
else say 'verification failed with' errs "errors."
exit /*stick a fork in it, we're done.*/
/*────────────────────────────────────────────────────────────────────────────*/
ffr: procedure expose r. s. rr.; parse arg n /*obtain the number from the arg.*/
if r.n\==0 then return r.n /*Defined? Then return the value.*/
_=ffr(n-1) + ffs(n-1) /*calculate the FFR & FFS values.*/
r.n=_; rr._=1; return _ /*assign value to R & RR; return.*/
/*────────────────────────────────────────────────────────────────────────────*/
ffs: procedure expose r. s. rr.; parse arg n /*search for ¬null R or S number.*/
if s.n==0 then do k=1 for n /* [↓] 1st IF is a SHORT CIRCUIT*/
if s.k\==0 then if r.k\==0 then iterate
call ffr k /*define R.k via FFR subroutine*/
km=k-1; _=s.km+1 /*the next S number, possibly.*/
_=_+rr._; s.k=_ /*define an element of S array.*/
exit /*stick a fork in it, we're all done. */
/*──────────────────────────────────────────────────────────────────────────────────────*/
FFR: procedure expose r. rr. s.; parse arg n /*obtain the number from the arguments.*/
if r.n\==0 then return r.n /*R.n defined? Then return the value.*/
_=FFR(n-1) + FFS(n-1) /*calculate the FFR and FFS values.*/
r.n=_; rr._=1; return _ /*assign the value to R & RR; return.*/
/*──────────────────────────────────────────────────────────────────────────────────────*/
FFS: procedure expose r. s. rr.; parse arg n /*search for not null R or S number. */
if s.n==0 then do k=1 for n /* [↓] 1st IF is a SHORT CIRCUIT. */
if s.k\==0 then if r.k\==0 then iterate /*are both defined?*/
call FFR k /*define R.k via the FFR subroutine*/
km=k-1; _=s.km+1 /*calc. the next S number, possibly.*/
_=_+rr._; s.k=_ /*define an element of the S array. */
end /*k*/
return s.n /*return S.n value to the invoker*/
/*────────────────────────────────────────────────────────────────────────────*/
ser: errs=errs+1; say '***error***!' arg(1); return
return s.n /*return S.n value to the invoker. */
/*──────────────────────────────────────────────────────────────────────────────────────*/
ser: errs=errs+1; say '***error***' arg(1); return