checkpoint
authorThomas Walker Lynch <eknp9n@reasoningtechnology.com>
Tue, 1 Apr 2025 03:06:31 +0000 (03:06 +0000)
committerThomas Walker Lynch <eknp9n@reasoningtechnology.com>
Tue, 1 Apr 2025 03:06:31 +0000 (03:06 +0000)
16 files changed:
developer/ccπŸ–‰/cpp_ext_0.c
developer/ccπŸ–‰/cpp_ext_1.c
developer/documentπŸ–‰/cpp.txt [deleted file]
developer/documentπŸ–‰/cpp_evaluation.org
developer/documentπŸ–‰/cpp_grammar.org
developer/example_cpp/0_readme.org
developer/example_cpp/cpp_ext_0.c [deleted file]
developer/example_cpp/cpp_ext_1.c [deleted file]
developer/example_cpp/try_1_exists.c [deleted file]
developer/example_cpp/try_2_connectors.c [deleted file]
developer/example_cpp/try_3_eq.c [deleted file]
developer/example_cpp/try_4_if.c [deleted file]
developer/example_cpp/try_5_access.c [deleted file]
developer/example_cpp/try_6_list.c [deleted file]
developer/example_cpp/try_ext_0.c [new file with mode: 0644]
developer/example_cpp/try_ext_1.c [new file with mode: 0644]

index 9b90e07..e196e92 100644 (file)
@@ -5,54 +5,14 @@
 
     documents in $REPO_HOME/developer/documentπŸ–‰
 
-1. Provides:
+1. We use a truth of existence
 
-  Raw constants: ZERO, ONE, COMMA, SEMICOLON
+   An empty value is false. Anything else is true. Hence, even the token '0' is true.
 
-  Token tagging: _TWION_0, _TWION_1
+2. todo
 
-  Controlled concatenation: CAT2, CAT3, CAT4
-
-  Existence (now EXISTS) with token safety via ##
-
-  Rewrite matchers: MATCH_RWR, NOT_MATCH_RWR
-
-  Logical base: _AND, _OR, _NOT, BOOL, EQ, NOT_EQ
-
-  Structural access: FIRST, REST, SECOND, THIRD
-
-  Branching: IF_ELSE(...), with macro-safe conditioning
-
-  Tests for all major features: try_eq.c, try_access.c, try_3_if.c, etc.
-
-2.
-  These are the non-recursive extensions.  See cpp_ext_1 for the recursive extensions.
-3.
-  The 'twion' is cute. It is reminiscent of a complex number in math. Like the complex number that is fed into scalar equestions.  The twion is a pair given to functions that only take singletons.
-
-4.
-  0 is false
-  1 is true
-
-  Macros starting with an '_' (underscore) are private.
-
-  EQ comparisons apart from logic comparisons, must be registered in advance. They take the form of, EQ__<x>__oo__<y>, note comments below.
-
-5. todo
-
-cpp_ext as separate project
-make the try into tests
-make EXISTS true, leave an empty element as false, NOT() would then be 'true'
-
-IS_LIST to distinguish element from list, though it will be tough to
-detect IS_LIST on a list with NOT_EXISTS elements,  then a list with all
-empty elements is still a list, still exits.
-
-mv BOOL AND OR 
-make AND and OR versions of FIND on EXISTS  (existence quantification)
-
-find a better name for NULL_FN
+- cpp_ext as separate project
+- make the try into tests
 
 */
 
@@ -87,23 +47,11 @@ Constants
 #define _TWION_0 ~,0
 #define _TWION_1 ~,1
 
-// RWR == rewrite rule, RWR_ is followed by macro name it is used in `_<name>_`
-// Matching text is replaced with nothing, making it empty
-// Potential for aliasing if x or y values have '__oo__' embedded in them.
-#define _RWR_NOT__0 
-#define _RWR_AND__1__oo__1
-#define _RWR_OR__0__oo__0
-
-// add more of this form to register other equivalences
-#define EQ__0__oo__0
-#define EQ__1__oo__1
-
 /*===========================================================================
-Primitive Concatenation
-  Not due to elegance, as `##` is convenient, rather this is 
-  used to force evaluation of arguments before `##`.
-  There will be a recursive CAT of n things in cpp_ext_1.c
-===========================================================================*/
+Fixed arg count concatenation
+
+  Not implemented for elegance, rather CAT is used to force evaluation of arguments before `##`.
+*/
 
 #define _CAT2(a ,b) a ## b
 #define CAT2(a ,b) _CAT2(a ,b)
@@ -115,129 +63,208 @@ Primitive Concatenation
 #define CAT4(a ,b ,c ,d) _CAT4(a ,b ,c ,d)
 
 /*===========================================================================
-Existence
-===========================================================================*/
+LOGIC
+
+  empty - false
+  NOT() - not empty, is true
+*/
 
   //----------------------------------------
   // primitive access
 
-  // note: _FIRST(), means passing an empty_item as the first item
-  // so it will return empty.
+  //  _FIRST with zero arguments returns nothing, otherwise returns first token
+  //  in the list, which can also be nothing.  e.g. _FIRST(,2,3) returns nothing.
   #define _FIRST(a ,...) a
+
+  //  _SECOND must be given a list of length 2, though no tokens need be given
   #define _SECOND(a ,b ,...) b
 
   //----------------------------------------
-  // existence
+  // given one or zero arguments, returns nothing
   //
-  // `##` prevents rewrite of _TWION_ in the _EXISTS_ITEM_1 macro, don't
-  // replace that with CAT!
-
-  #define _EXISTS_ITEM_2(x_item) _SECOND(x_item ,1) 
-  #define _EXISTS_ITEM_1(x_item) _EXISTS_ITEM_2(_TWION_0##x_item)
+  #define RETURN_NOTHING()
 
-  #define EXISTS_ITEM(x_item)   _EXISTS_ITEM_1(x_item)
-  #define EXISTS(...) EXISTS_ITEM( _FIRST(__VA_ARGS__) )
+  //----------------------------------------
+  // given a list returns a token
+  // given an token returns a token
+  // given nothing, returns nothing
+  //
+  #define _OR(...) _FIRST(RETURN_NOTHING __VA_ARGS__ ())
+
+  /*----------------------------------------
+   given a token returns nothing
+   given nothing returns 1
+
+   `##` prevents rewrite of _TWION_ in the _EXISTS_TOKEN_1 macro, don't
+   replace that with CAT!   
+  */
+  #define _NOT_TOKEN_ss(x_token) _SECOND(x_token ,) 
+  #define _NOT_TOKEN_s(x_token)  _NOT_TOKEN_ss(_TWION_1##x_token)
+  #define _NOT_TOKEN(x_token)   _NOT_TOKEN_s(x_token)
+
+  /*----------------------------------------
+   given a token or a list, returns nothing
+   given nothing, returns 1
+  */
+  #define NOT(...) _NOT_TOKEN( _OR(__VA_ARGS__) )
+
+  /*----------------------------------------
+   given argument is empty returns empty
+   given argument is not empty, returns 1
+  */
+  #define EXISTS(...) NOT( NOT(__VA_ARGS__) )
+
+  // useful synonym
+  #define MATCH_RWR(x) NOT(x)
 
-  #define _NOT_EXISTS_ITEM_2(x_item) _SECOND(x_item ,0) 
-  #define _NOT_EXISTS_ITEM_1(x_item) _NOT_EXISTS_ITEM_2(_TWION_1##x_item)
+/*===========================================================================
+  IF-ELSE construct.
+  Usage: IF_ELSE(condition)(<true case>)(<false case>)
 
-  #define NOT_EXISTS_ITEM(x_item)   _NOT_EXISTS_ITEM_1(x_item)
-  #define NOT_EXISTS(...) NOT_EXISTS_ITEM( _FIRST(__VA_ARGS__) )
+  A most amazing little macro. It has no dependencies on the other macros
+  in this file, though many of those will be useful in predicates
+*/
 
-  // useful to use with rewrite rules that substitute to nothing
-  #define MATCH_RWR(x_item) NOT_EXISTS(x_item)
-  #define NOT_MATCH_RWR(x_item) EXISTS(x_item)
+  #define IF(...)  CAT2(_IF_ ,EXISTS(__VA_ARGS__))
+  #define _IF_1(...)          __VA_ARGS__ _IF_1_ELSE
+  #define _IF_(...)                       _IF__ELSE
+  #define _IF_1_ELSE(...)
+  #define _IF__ELSE(...)      __VA_ARGS__
 
 /*===========================================================================
-Logic Connectors
-===========================================================================*/
 
-  #define _NOT(x_item) \
-    MATCH_RWR( CAT2(_RWR_NOT__ ,x_item) )
+  In cpp_ext logic:
+    Ξ΅  is false and anything else is true
+
+  In BOOLEAN logic
+    Ξ΅ is an error, 0 is false, anything else is true
 
-  #define _AND(x_item ,y_item) \
-    MATCH_RWR( CAT4(_RWR_AND__ ,x_item ,__oo__ ,y_item) )
+  USE this operator to convert something in cpp_ext logic to something for
+  the built-in operators.
 
-  #define _OR(x_item ,y_item) \
-    NOT_MATCH_RWR( CAT4(_RWR_OR__ ,x_item ,__oo__ ,y_item) )
+  Note the output of BOOLEAN is always an existing token, so it will
+  aways be 'true' in cpp_ext logic.
+
+*/
+  #define BOOLEAN(...) IF(__VA_ARGS__) (1) (0)
 
-  #define _BOOL(x_item) \
-    _AND( \
-       EXISTS_ITEM( x_item ) \
-      ,NOT_MATCH_RWR( CAT2(EQ__0__oo__ ,x_item) )  \
-    )
-  #define BOOL(x_item) _BOOL(_FIRST(x_item))
-  
-  #define NOT(x_item)         _NOT(BOOL(x_item))
-  #define AND(x_item ,y_item) _AND(BOOL(x_item) ,BOOL(y_item))
-  #define  OR(x_item ,y_item)  _OR(BOOL(x_item) ,BOOL(y_item))
 
 /*===========================================================================
-  Equality
+  Logic connectors
+*/
+  #define LEQ2(x ,y) IF(x) (y) (NOT(y))
+  #define XOR2(x ,y) IF(x) (NOT(y)) (y)
+  #define AND2(x ,y) IF(x) (y) ()
+  #define  OR2(x ,y) IF(x) (1) (y)
+
+
+/*===========================================================================
+  Registered Equivalence
 
-  more general than a connector because more rules can be added.
+  Checks if x and y have been paired in a rewrite rule.
 
-  each registered equality rule has the form
+  Logic values can not be paired, as anything except an empty argument is taken as true.
+
+  each pairing rule has the form
      EQ__<x>__oo__<y>
-  for example, logic equalities are already registered:
-     EQ__0__oo__0
-     EQ__1__oo__1
 
-===========================================================================*/
+  for example:
+    #define EQ__APPLE__oo__APPLE
+    #define EQ__PEAR__oo__PEAR
 
-  #define EQ(x_item ,y_item) \
-        MATCH_RWR( CAT4(EQ__ ,x_item ,__oo__ ,y_item) )
+    SHOW( EQ(APPLE ,APPLE) ); -> 1
+    SHOW( EQ(APPLE ,PEAR) ); -> Ξ΅
 
-  #define NOT_EQ(x_item ,y_item) \
-    NOT_MATCH_RWR( CAT4(EQ__ ,x_item ,__oo__ ,y_item) )
+  // if empty should be EQ to empty, add this
+  // without this, EQ(,) -> Ξ΅
+  #define EQ____oo__
 
-/*===========================================================================
-  IF-ELSE construct.
-  Usage: IF_ELSE(condition)(<true case>)(<false case>)
+===========================================================================*/
 
-  A most amazing little macro. It has no dependencies on the other macros
-  in this file, though many will be useful for setting (condition)
+  // if empty should be EQ to empty, keep this
+  // without this, EQ(,) -> Ξ΅
+  #define EQ____oo__
 
-  The seemingly extra layer prevents BOOL_(condition) from being pasted with a ## which, if done, would prevent it from being evaluated.  Recall, the first step in evaluation is a literal copy in of the arguments.  ===symbol ========================================================================*/
+  #define EQ__0__oo__0
+  #define EQ__1__oo__1
 
-  #define IF(predicate)  CAT2(_IF_ ,BOOL(predicate))
-  #define _IF_1(...)          __VA_ARGS__ _IF_1_ELSE
-  #define _IF_0(...)                      _IF_0_ELSE
-  #define _IF_1_ELSE(...)
-  #define _IF_0_ELSE(...)      __VA_ARGS__
+  #define EQ(x_token ,y_token) MATCH_RWR( CAT4(EQ__ ,x_token ,__oo__ ,y_token) )
 
 /*===========================================================================
-Access
-    see ext_1 with recursion for `Nth`
-
+Remainder of list
 ===========================================================================*/
 
-  // _FIRST defined in the logic section
-  #define FIRST(pad ,...)\
-    IF \
-      ( NOT_EXISTS(__VA_ARGS__) ) \
-      (pad)                       \
-      ( _FIRST(__VA_ARGS__) )  
-
   #define _REST(a ,...) __VA_ARGS__
   #define REST(...)\
     IF \
-      ( NOT_EXISTS(__VA_ARGS__) ) \
-      ()                          \
-      ( _REST(__VA_ARGS__) )  
-
-  // _SECOND defined in the logic section
-  #define SECOND(pad ,...) \
-    IF \
-      ( NOT_EXISTS(__VA_ARGS__) ) \
-      (pad)                       \
-      ( _SECOND(__VA_ARGS__ ,pad) )  
-
-  #define _THIRD(a ,b ,c ,...) c
-  #define THIRD(pad ,...) \
-    IF \
-      ( NOT_EXISTS(__VA_ARGS__) ) \
-      (pad)                       \
-      ( _THIRD(__VA_ARGS__ ,pad, pad) )  
+      (__VA_ARGS__)            \
+      ( _REST(__VA_ARGS__) ) \
+      ()
 
 #endif
+/*
+  _FIRST(1) -> 1
+  _FIRST() -> 
+  _SECOND(1,2) -> 2
+  _SECOND(1,) -> 
+
+  RETURN_NOTHING() -> 
+
+  _OR() -> 
+  _OR(1) -> RETURN_NOTHING 1 ()
+  _OR(1,2,3) -> RETURN_NOTHING 1
+
+  T(x) -> 7
+  _NOT_ITEM() -> _NOT_ITEM()
+  _NOT_ITEM(1) -> _NOT_ITEM(1)
+  _NOT_ITEM(T(x)) -> _NOT_ITEM(7)
+
+  NOT() -> 1
+  NOT(1) -> 
+  NOT(T(x)) -> 
+  NOT(1,2,3) -> 
+
+  BOOL() -> BOOL()
+  CAT2(_IF_ ,BOOL()) -> _IF_BOOL()
+
+  TO_1_OR_0() -> TO_1_OR_0()
+  TO_1_OR_0(1) -> TO_1_OR_0(1)
+  TO_1_OR_0(x) -> TO_1_OR_0(x)
+  TO_1_OR_0(1.2.3) -> TO_1_OR_0(1.2.3)
+
+  EXISTS() -> 
+  EXISTS(0) -> 1
+  EXISTS(x,y,z) -> 1
+
+  LEQ2( , ) -> 1
+  LEQ2( , 1 ) -> 
+  LEQ2( 1, ) -> 
+  LEQ2( 1, 0 ) -> 0
+
+  XOR2( , ) -> 
+  XOR2( , 0 ) -> 0
+  XOR2( 0, 0 ) -> 
+
+  AND2( , 0 ) -> 
+  AND2( 0, 1 ) -> 1
+
+  OR2( , ) -> 
+  OR2( , 0 ) -> 0
+
+  EQ(APPLE ,APPLE) -> 1
+  EQ(APPLE ,PEAR) -> 
+  EQ(PEAR ,PEAR) -> 1
+  EQ(,) -> 1
+  EQ(,PEAR) -> 
+  EQ(PEAR ,) -> 
+
+  BOOLEAN() -> 0
+  BOOLEAN(0) -> 1
+  BOOLEAN(foo) -> 1
+  BOOLEAN(1,2,3) -> 1
+
+  REST() -> 
+  REST(1) -> 
+  REST(1,2) -> 2
+  REST(1,2,3) -> 2,3
+*/
index a188507..5f8a5b4 100644 (file)
@@ -8,17 +8,12 @@ To be added:
 
 LIST_TOO_LONG
   
-// scanning left to right finds first that exists
-LEFTMOST_EXISTENT 
+cleanup list
+DROP_EMPTY_ALL
+DROP_EMPTY_LEFT
+DROPE_EMPTY_RIGHT
 
-// scanning left to right finds last that exits
-RIGHTMOST_EXISTENT
-
-DROP_NOT_EXISTS_ALL
-DROP_NOT_EXISTS_LEFT
-DROPE_NOT_EXISTS_RIGHT
-
-#define _CAT(sep,first,...)                              \
+#define CAT(sep,first,...)                              \
 
 */
 
@@ -30,61 +25,141 @@ DROPE_NOT_EXISTS_RIGHT
   This chain of EVAL macros forces the preprocessor to perform many rescans,
   which is necessary to β€œunroll” recursive macros.
 ===========================================================================*/
-//#define EVAL(...)            EVAL1024(__VA_ARGS__)
-#define EVAL(...)            EVAL32(__VA_ARGS__)
-#define EVAL1024(...)        EVAL512(EVAL512(__VA_ARGS__))
-#define EVAL512(...)         EVAL256(EVAL256(__VA_ARGS__))
-#define EVAL256(...)         EVAL128(EVAL128(__VA_ARGS__))
-#define EVAL128(...)         EVAL64(EVAL64(__VA_ARGS__))
-#define EVAL64(...)          EVAL32(EVAL32(__VA_ARGS__))
-#define EVAL32(...)          EVAL16(EVAL16(__VA_ARGS__))
-#define EVAL16(...)          EVAL8(EVAL8(__VA_ARGS__))
-#define EVAL8(...)           EVAL4(EVAL4(__VA_ARGS__))
-#define EVAL4(...)           EVAL2(EVAL2(__VA_ARGS__))
-#define EVAL2(...)           EVAL1(EVAL1(__VA_ARGS__))
-#define EVAL1(...)           __VA_ARGS__
+  //#define EVAL(...)            EVAL1024(__VA_ARGS__)
+  #define EVAL(...)            EVAL32(__VA_ARGS__)
+  #define EVAL1024(...)        EVAL512(EVAL512(__VA_ARGS__))
+  #define EVAL512(...)         EVAL256(EVAL256(__VA_ARGS__))
+  #define EVAL256(...)         EVAL128(EVAL128(__VA_ARGS__))
+  #define EVAL128(...)         EVAL64(EVAL64(__VA_ARGS__))
+  #define EVAL64(...)          EVAL32(EVAL32(__VA_ARGS__))
+  #define EVAL32(...)          EVAL16(EVAL16(__VA_ARGS__))
+  #define EVAL16(...)          EVAL8(EVAL8(__VA_ARGS__))
+  #define EVAL8(...)           EVAL4(EVAL4(__VA_ARGS__))
+  #define EVAL4(...)           EVAL2(EVAL2(__VA_ARGS__))
+  #define EVAL2(...)           EVAL1(EVAL1(__VA_ARGS__))
+  #define EVAL1(...)           __VA_ARGS__
 
 /*===========================================================================
   Defer macros: these help β€œhide” recursive calls for additional expansion passes.
 ===========================================================================*/
-#define NULL_FN()
-#define DEFER1(m)            m NULL_FN()
-#define DEFER2(m)            m NULL_FN NULL_FN()()
-#define DEFER3(m)            m NULL_FN NULL_FN NULL_FN()()()
-#define DEFER4(m)            m NULL_FN NULL_FN NULL_FN NULL_FN()()()()
+// defined in cpp_ext_0: RETURN_NOTHING()
+
+  #define DEFER1(m) \
+    m RETURN_NOTHING()
+  #define DEFER2(m) \
+    m RETURN_NOTHING RETURN_NOTHING()()
+  #define DEFER3(m) \
+    m RETURN_NOTHING RETURN_NOTHING RETURN_NOTHING()()()
+  #define DEFER4(m) \
+    m RETURN_NOTHING RETURN_NOTHING RETURN_NOTHING RETURN_NOTHING()()()()
+  #define DEFER5(m) \
+    m RETURN_NOTHING RETURN_NOTHING RETURN_NOTHING RETURN_NOTHING RETURN_NOTHING()()()()()
 
 /*===========================================================================
-  Quantifiers
-===========================================================================*/
+  Find an item in a list
+
+  number of EVALs required depends upon length of not found list prefix
+
+  REST will return nothing on one of two conditions, that the list has
+  been exhausted, or that the list is about to exhausted, it has nothing
+  after the last comma. To assure that a tailing item always gets sent
+  to the predicate, even when empty, we append an empty item.
 
-#define _FIND(predicate ,...) \
+===========================================================================*/
+  // defined in cpp_ext_0: _FIRST(a ,...) a 
+
+  // returns found item or EOL()
+  #define _FIND(predicate ,...) \
+    IF \
+      (__VA_ARGS__) \
+      (IF \
+        ( predicate(_FIRST(__VA_ARGS__)) ) \
+        ( _FIRST(__VA_ARGS__) ) \
+        ( DEFER3(_FIND_CONFEDERATE)()(predicate ,REST(__VA_ARGS__)) ) \
+        ) \
+      (EOL()) 
+  #define _FIND_CONFEDERATE() _FIND
+  #define FIND(predicate ,...) EVAL( _FIND(predicate ,__VA_ARGS__ ,) )
+
+  // true if list exhausted, false otherwise
+  #define _WHILE(predicate ,...) \
+    IF \
+      (__VA_ARGS__) \
+      (IF \
+        ( predicate(_FIRST(__VA_ARGS__)) ) \
+        ( DEFER3(_WHILE_CONFEDERATE)()(predicate ,REST(__VA_ARGS__)) ) \
+        () \
+        ) \
+      (1) 
+  #define _WHILE_CONFEDERATE() _WHILE
+  #define WHILE(predicate ,...) EVAL( _WHILE(predicate ,__VA_ARGS__ ,) )
+
+  // returns true or false
+  #define _HAS_ITEM(item ,...) \
+    IF \
+      (__VA_ARGS__) \
+      (IF \
+        ( EQ(item ,_FIRST(__VA_ARGS__)) ) \
+        ( 1 ) \
+        ( DEFER3(_HAS_ITEM_CONFEDERATE)()(item ,REST(__VA_ARGS__)) ) \
+        ) \
+      () 
+  #define _HAS_ITEM_CONFEDERATE() _HAS_ITEM
+  #define HAS_ITEM(predicate ,...) EVAL( _HAS_ITEM(predicate ,__VA_ARGS__ ,) )
+
+  // if no list, returns EOL(), else returns last item in the list
+  #define _LAST(...) \
+    IF \
+      (__VA_ARGS__) \
+      ( _LAST_s(_FIRST(__VA_ARGS__) ,REST(__VA_ARGS__)) ) \
+      (EOL())
+  #define _LAST_s(item, ...) \
+    IF \
+      (__VA_ARGS__) \
+      ( DEFER3(_LAST_s_CONFEDERATE)()(_FIRST(__VA_ARGS__) ,REST(__VA_ARGS__)) ) \
+      (item)
+  #define _LAST_s_CONFEDERATE() _LAST_s
+  #define LAST(...) EVAL( _LAST(__VA_ARGS__ ,) )
+
+  // join tokens with a separator in between, separator can have nothing as a value
+
+
+#define _CAT(sep ,...) \
   IF \
-    ( NOT_EXISTS(__VA_ARGS__) ) \
-    () \
-    (IF \
-      ( predicate(FIRST(,__VA_ARGS__)) )         \
-      ( FIRST(,__VA_ARGS__) )                    \
-      ( DEFER3(_FIND_CONFEDERATE) ()(predicate ,REST(__VA_ARGS__)) )     \
-     )
-#define _FIND_CONFEDERATE() _FIND
-
-// number of evals required depends upon length of not found list prefix
-#define FIND(predicate ,...) EVAL( _FIND(predicate ,__VA_ARGS__) )
-
-#define _FIND_ITEM(item ,...) \
+    (__VA_ARGS__) \
+    (_CAT_s(sep ,__VA_ARGS__)) \
+    ()
+
+#define _CAT_s(sep ,a ,...) \
   IF \
-    ( NOT_EXISTS(__VA_ARGS__) ) \
-    () \
-    (IF \
-      ( EQ(item ,FIRST(,__VA_ARGS__)) )          \
-      ( item )                    \
-      ( DEFER3(_FIND_ITEM_CONFEDERATE) ()(item ,REST(__VA_ARGS__)) )     \
-     )
-#define _FIND_ITEM_CONFEDERATE() _FIND_ITEM
-
-// number of evals required depends upon length of not found list prefix
-#define FIND_ITEM(predicate ,...) EVAL( _FIND_ITEM(predicate ,__VA_ARGS__) )
+    (__VA_ARGS__) \
+    ( CAT3( a ,sep ,DEFER5(_CAT_s_CONFEDERATE())(sep ,__VA_ARGS__)) )  \
+    (a)
+
+#define _CAT_s_CONFEDERATE() _CAT_s
+
+#define CAT(...) EVAL( _CAT(__VA_ARGS__ ,) )
+
+
+
+/*===========================================================================
+  Quantifiers
+===========================================================================*/
+
+  // AKA all quantification, returns true or false
+  #define AND(...) WHILE(EXISTS ,__VA_ARGS__)
+
+  // AKA existence quantification, returns true or false
+  #define OR(...)  NOT(WHILE(NOT ,__VA_ARGS__)
+
+/*===========================================================================
+  Access
+===========================================================================*/
 
+  #define FIRST(...) \
+    IF( __VA_ARGS__ ) \
+      ( _FIRST(__VA_ARGS__) ) \
+      (EOL())
 
 
 #endif  
diff --git a/developer/documentπŸ–‰/cpp.txt b/developer/documentπŸ–‰/cpp.txt
deleted file mode 100644 (file)
index 3896b03..0000000
+++ /dev/null
@@ -1,184 +0,0 @@
-
-The twions do for cpp what complex numbers do for mathematics. A two dimensional value used with a structure designed for one dimensional values.
-
-/*
-Code in this file is based on: https://github.com/18sg/uSHET/blob/master/lib/cpp_magic.h 
-see tutorial at: http://jhnet.co.uk/articles/cpp_magic
-
-----------------------------------------
-1. Issues
-
-1.1 Empty argument name is still a name
-
-  `##` arguments are not evaluated so, for example:
-  ```
-  #define cat(x,y) x##y
-  #define xx 3
-  #define yy 5
-  cat(xx,yy) --> xxyy
-  ```
-  xx and yy are not rewritten.
-
-  For my cpp with an empty __VAR_ARGS__ is still acting like it exists with a##__VAR_ARGS__ as though it expands out to a##<empty>. To make the empty args empty, we must pass through from a macro that does not use `##` on them. I guess this also applies to
-  other empty arguments. Thus <empty> is taken literally as were `xx` and `yy` in the
-  example above, though it does not have a name as do `xx` and `yy`.
-
-  Hence instead of calling
-
-    #define IS_EMPTY_ITEM(x_item) _IS_EMPTY_2(_TWION_##x_item)
-
-  We have
-
-  #define _IS_EMPTY_1(x_item) _IS_EMPTY_2(_TWION_##x_item)
-  #define IS_EMPTY_ITEM(x_item) _IS_EMPTY_1(x_item)
-
-1.1 function macro definition - no space between the macro name and the parameter
-  list.
-
-  #define sum(p ,q ,r) (p + q + r) // good
-
-  #define sum (p ,q ,r) (p + q + r) // defines rewrite sum -> (p ,q ,r) (p + q + r)
-
-----------------------------------------
-2. cpp 
-
-2.1 grammar
-
-  identifier = [_a-zA-Z][_a-zA-Z0-9]*
-             | ([_a-zA-Z\u00A0-\uFFFF])([_a-zA-Z0-9\u00A0-\uFFFF])*
-
-  macro_name = identifier
-
-  token = identifier
-        | number              ; e.g., 42, 0xFF, 3.14
-        | string_literal      ; "hello"
-        | character_constant  ; 'a', '\n'
-        | operator_token      ; +, -, ~, <<, etc.
-        | punctuation         ; (), [], {}, etc. (when tokenized)
-        | parenthesized_expr  ; (1,2), (x + y)
-
-  empty_item = Ξ΅  
-     An item with no content, but syntactically present and contributing to list length.
-     For example, ( , ) is a two-item arg_list with two empty_items.
-
-  shim_item = ~,1
-     A special two-token item treated as a single item.
-     Its role is to shift the remaining members of a list by one position when prepended.
-     An honorary member of the single item club.
-
-  item = token | empty_item | shim_item
-
-  arg_list = item (, item)* ; comma-separated list of items
-
-  pair     = item , item ; exactly two items
-
-2.2 'private' identify 
-
-  By convention private identifiers begin with an `_` character. 
-
-  Macros with this prefix are not intended to be called by users, and
-  indentifiers with this prefix are not intended to to used.
-
-----------------------------------------
-3. Logic
-
-  2.1 Logic Values
-
-   False: 0
-    True: 1
-
-  2.2 One Item Arguments
-
-  Some logic functions are required to be given a single item, i.e. to not be given a list.. This requirement is maintained by the manner they are used. For example, being passed a value gotten by FIRST.
-
-  Macro arguments that must be single items are suffixed with `_item`.
-
-*/
-
-EMPTYNESS
-
-2. Empty argument list query 
-
-2.1 if empty values are allowed for arguments
-
-  There is a nuance when checking that a list is empty, because lists can
-  have empty elements.  E.g.   `a ,b , ,d ,e`   including leading elements or
-  even all empty elements, e.g. `, , , ,`.
-
-  Hence, if we use the first element to represent that a list argument is present, we might happen upon an empty first element.  Even if we CAT all the elements for a long list of empty values, we can produce an empty element.
-
-  We can not overload macro definitions with different argument counts, this is
-  not allowed.
-
-2.2 when empty elements should not happen 
-
-  Fortunately, in many applications empty elements do not have meaning. In
-  such applications, if the first element is not empty, we can we conclude
-  there is a list, rather than an empty list.
-
-  Access of the nth element is more fundamental than logic, so access can be
-  used.
-
-  Note this simplified implementation for SECOND:
-
-   #define SECOND_1(a ,b ,...) b
-   #define SECOND(...) SECOND_1(__VA_ARGS__, pad)
-
-  Notice that if __VA_ARGS__ is empty, that it will become the empty
-  `a` value in SECOND.  Thus SECOND_1 will always be given at least
-  one argument, even when SECOND is given no arguments!
-
-  In contrast to access, the variadic CAT function relies upon having
-  an predicate to detect emptiness so as to stop the recursion, so it
-  is not possible to use to CAT all the elements of a list to see that
-  some elements are not empty.
-
-2.3 Getting different behavior from an empty __VA_ARGS__ and a non-empty one.
-
-  2.3.1 peek-a-boo macro call
-
-  The primary trick is this:
-
-     macro __VA_ARGS__ ()
-
-  The macro will only be called when it is followed by parens, so it will only be called when __VA_ARGS__ is empty.  However when __VA_ARGS__ is not empty we have a mess. Say it is a,b,c.  Then:
-
-     macro a,b,c () -> macroa,b,c()
-
-  That is three elements ending in a macro call `c()` which is surely unintentional.
-  Suppose we instead do:
-
-     macro FIRST(__VA_ARGS_) () -> macro a () -> macroa()
-
-  Which is another macro call, though probably not one that is defined.  If
-  the first argument in the __VA_ARGS__ list is empty, then we are back to
-  `macro()` - indistinguishable from a call with an empty argument list.
-
-  2.3.1 rewrite rule
-  
-  Another approach is to use a rewrite rule:
-
-      #define rewrite_rule new_value
-
-      then in the macro: 
-
-          rewrite __VA_ARGS__   
-
-      when __VARGS__ is empty:
-
-          rewrite##__VA_ARGS__##rule   ->  rewrite_rule -> new_value
-
-      when __VARGS__ is, say, a,b,c:
-      
-          rewrite##a,b,c##_rule  ->  rewritea,b,c_rule
-
-      which is a rather messed up three item list. If we use FIRST on the middle
-      string:
-
-           -> rewritea_rule
-      
-       Which is a 1 element list.
-
-      (Note, `##` is evaluate before the macro expansions.)
-
-   
index b320ac4..5c6a493 100644 (file)
@@ -4,6 +4,9 @@
 
 1. Macro function definition
 
+   Macro function definitions are not evaluated, so macro calls in them remain
+   literal.
+
    A macro function has three parts, 1) a name 2) a parameter list  3) body
 
    Parameters are declared by listing them between parenthesis after the name. No space
index ef88176..98e5154 100644 (file)
@@ -14,19 +14,34 @@ Grammar
         | parenthesized_expr  ; (1,2), (x + y)
 
   empty_item = Ξ΅  
-     An item with no content, but syntactically present and contributing to list length.
-     For example, ( , ) is a two-item arg_list with two empty_items.
+     This stands for nothing. It is useful for talking about item lists, because in general lists can have empty slots. Remember cpp works with literal text.
 
-  shim_item = ~,1
-     A special two-token item treated as a single item.
-     Its role is to shift the remaining members of a list by one position when prepended.
-     An honorary member of the single item club.
+     For example, ( , ) is a length 2 list with two empty slots.
+
+     For example, (1,,2) is a length 3 three list with one empty slot.
+
+     On calls, the length of the arg_list must match length of the parameter list.
+
+     For example, _FIRST() has a first parameter that expands to nothing if it is referenced
+       #define _FIRST(a ,...) a
+       _FIRST() --> Ξ΅ is not a bad argument count error, but instead expands to nothing
 
-  item = token | empty_item | shim_item
+  general_list = token (, token | Ξ΅)*
+     Comma-separated list of items. Commas can appear without tokens between them.
+
+  arg_list = general_list
+
+  pair  = token | Ξ΅ , token | Ξ΅; exactly two tokens.
+
+  twion = pair
+     A special two-token list given to certain macros in a place one token is expected.
+     Its role is to shift the remaining members of a list by one position when prepended.
+     An honorary member of the single token club. A common twion is `~,1`
 
-  arg_list = item (, item)* ; comma-separated list of items
+  parm_list = identifier (, identifier)* ; comma-separated list of identifiers
+     A parameter list differs from a general list in that two commas can not
+     appear adjacent to each other, and all members are identifiers.
 
-  pair     = item , item ; exactly two items
 
 2.2 'private' identify 
 
index d10769b..cb3056f 100644 (file)
@@ -1,4 +1,4 @@
-These are direct built one at a time, for example:
+These examples are directly built one at a time, for example:
 
    #+BEGIN_SRC bash
    > gcc try_6_list.c 
diff --git a/developer/example_cpp/cpp_ext_0.c b/developer/example_cpp/cpp_ext_0.c
deleted file mode 100644 (file)
index 573c27c..0000000
+++ /dev/null
@@ -1,245 +0,0 @@
-/*
-  See also 
-    https://github.com/18sg/uSHET/blob/master/lib/cpp_magic.h 
-    and tutorial at: http://jhnet.co.uk/articles/cpp_magic
-
-    documents in $REPO_HOME/developer/documentπŸ–‰
-
-1. Provides:
-
-  Raw constants: ZERO, ONE, COMMA, SEMICOLON
-
-  Token tagging: _TWION_0, _TWION_1
-
-  Controlled concatenation: CAT2, CAT3, CAT4
-
-  Existence (now EXISTS) with token safety via ##
-
-  Rewrite matchers: MATCH_RWR, NOT_MATCH_RWR
-
-  Logical base: _AND, _OR, _NOT, BOOL, EQ, NOT_EQ
-
-  Structural access: FIRST, REST, SECOND, THIRD
-
-  Branching: IF_ELSE(...), with macro-safe conditioning
-
-  Tests for all major features: try_eq.c, try_access.c, try_3_if.c, etc.
-
-2.
-  These are the non-recursive extensions.  See cpp_ext_1 for the recursive extensions.
-3.
-  The 'twion' is cute. It is reminiscent of a complex number in math. Like the complex number that is fed into scalar equestions.  The twion is a pair given to functions that only take singletons.
-
-4.
-  0 is false
-  1 is true
-
-  Macros starting with an '_' (underscore) are private.
-
-  EQ comparisons apart from logic comparisons, must be registered in advance. They take the form of, EQ__<x>__oo__<y>, note comments below.
-
-5. todo
-
-cpp_ext as separate project
-make the try into tests
-make EXISTS true, leave an empty element as false
-
-IS_LIST to distinguish element from list, though it will be tough to
-detect IS_LIST on a list with NOT_EXISTS elements,  then a list with all
-empty elements is still a list, still exits.
-
-mv BOOL AND OR 
-make AND and OR versions of FIND on EXISTS  (existence quantification)
-
-find a better name for NULL_FN
-
-*/
-
-#ifndef CPP_EXT_0
-#define CPP_EXT_0
-
-/*===========================================================================
-DEBUG
-===========================================================================*/
-
-#include <stdio.h>
-#define DEBUG_CPP
-#define STR(...) #__VA_ARGS__
-
-// print the macro and the evaluation of the macro
-#define SHOW(expr) printf("%s -> %s\n", #expr, STR(expr))
-
-/*===========================================================================
-Constants
-===========================================================================*/
-
-#define COMMA ,
-#define SEMICOLON ;
-
-#define FALSE 0
-#define TRUE  1
-
-//---------
-
-#define _TWION_0 ~,0
-#define _TWION_1 ~,1
-
-// RWR == rewrite rule, RWR_ is followed by macro name it is used in `_<name>_`
-// Matching text is replaced with nothing, making it empty
-// Potential for aliasing if x or y values have '__oo__' embedded in them.
-#define _RWR_NOT__0 
-#define _RWR_AND__1__oo__1
-#define _RWR_OR__0__oo__0
-
-// add more of this form to register other equivalences
-#define EQ__0__oo__0
-#define EQ__1__oo__1
-
-/*===========================================================================
-Primitive Concatenation
-  Not due to elegance, as `##` is convenient, rather this is 
-  used to force evaluation of arguments before `##`.
-  There will be a recursive CAT of n things in cpp_ext_1.c
-===========================================================================*/
-
-#define _CAT2(a ,b) a ## b
-#define CAT2(a ,b) _CAT2(a ,b)
-
-#define _CAT3(a ,b ,c) a ## b ## c
-#define CAT3(a ,b ,c) _CAT3(a ,b ,c)
-
-#define _CAT4(a ,b ,c ,d) a ## b ## c ## d
-#define CAT4(a ,b ,c ,d) _CAT4(a ,b ,c ,d)
-
-#define APPEND(list ,...) list ,__VA_ARGS__
-
-
-
-/*===========================================================================
-Existence
-===========================================================================*/
-
-  //----------------------------------------
-  // primitive access
-
-  // note: _FIRST of nothing, _FIRST(), means passing an empty_item as the first item
-  // so it will return empty.
-  #define _FIRST(a ,...) a
-  #define _SECOND(a ,b ,...) b
-
-  //----------------------------------------
-  // existence
-  //
-  // `##` prevents rewrite of _TWION_ in the _EXISTS_ITEM_1 macro, don't
-  // replace that with CAT!
-
-  #define _EXISTS_ITEM_2(x_item) _SECOND(x_item ,1) 
-  #define _EXISTS_ITEM_1(x_item) _EXISTS_ITEM_2(_TWION_0##x_item)
-
-  #define EXISTS_ITEM(x_item)   _EXISTS_ITEM_1(x_item)
-  #define EXISTS(...) EXISTS_ITEM( _FIRST(__VA_ARGS__) )
-
-  #define _NOT_EXISTS_ITEM_2(x_item) _SECOND(x_item ,0) 
-  #define _NOT_EXISTS_ITEM_1(x_item) _NOT_EXISTS_ITEM_2(_TWION_1##x_item)
-
-  #define NOT_EXISTS_ITEM(x_item)   _NOT_EXISTS_ITEM_1(x_item)
-  #define NOT_EXISTS(...) NOT_EXISTS_ITEM( _FIRST(__VA_ARGS__) )
-
-  // useful to use with rewrite rules that substitute to nothing
-  #define MATCH_RWR(x_item) NOT_EXISTS(x_item)
-  #define NOT_MATCH_RWR(x_item) EXISTS(x_item)
-
-/*===========================================================================
-Logic Connectors
-===========================================================================*/
-
-  #define _NOT(x_item) \
-    MATCH_RWR( CAT2(_RWR_NOT__ ,x_item) )
-
-  #define _AND(x_item ,y_item) \
-    MATCH_RWR( CAT4(_RWR_AND__ ,x_item ,__oo__ ,y_item) )
-
-  #define _OR(x_item ,y_item) \
-    NOT_MATCH_RWR( CAT4(_RWR_OR__ ,x_item ,__oo__ ,y_item) )
-
-  #define _BOOL(x_item) \
-    _AND( \
-       EXISTS_ITEM( x_item ) \
-      ,NOT_MATCH_RWR( CAT2(EQ__0__oo__ ,x_item) )  \
-    )
-  #define BOOL(x_item) _BOOL(_FIRST(x_item))
-  
-  #define NOT(x_item)         _NOT(BOOL(x_item))
-  #define AND(x_item ,y_item) _AND(BOOL(x_item) ,BOOL(y_item))
-  #define  OR(x_item ,y_item)  _OR(BOOL(x_item) ,BOOL(y_item))
-
-/*===========================================================================
-  Equality
-
-  more general than a connector because more rules can be added.
-
-  each registered equality rule has the form
-     EQ__<x>__oo__<y>
-  for example, logic equalities are already registered:
-     EQ__0__oo__0
-     EQ__1__oo__1
-
-===========================================================================*/
-
-  #define EQ(x_item ,y_item) \
-        MATCH_RWR( CAT4(EQ__ ,x_item ,__oo__ ,y_item) )
-
-  #define NOT_EQ(x_item ,y_item) \
-    NOT_MATCH_RWR( CAT4(EQ__ ,x_item ,__oo__ ,y_item) )
-
-/*===========================================================================
-  IF-ELSE construct.
-  Usage: IF_ELSE(condition)(<true case>)(<false case>)
-
-  A most amazing little macro. It has no dependencies on the other macros
-  in this file, though many will be useful for setting (condition)
-
-  The seemingly extra layer prevents BOOL_(condition) from being pasted with a ## which, if done, would prevent it from being evaluated.  Recall, the first step in evaluation is a literal copy in of the arguments.  ===symbol ========================================================================*/
-
-  #define IF(predicate)  CAT2(_IF_ ,BOOL(predicate))
-  #define _IF_1(...)          __VA_ARGS__ _IF_1_ELSE
-  #define _IF_0(...)                      _IF_0_ELSE
-  #define _IF_1_ELSE(...)
-  #define _IF_0_ELSE(...)      __VA_ARGS__
-
-/*===========================================================================
-Access
-    see ext_1 with recursion for `Nth`
-
-===========================================================================*/
-
-  // _FIRST defined in the logic section
-  #define FIRST(pad ,...)\
-    IF \
-      ( NOT_EXISTS(__VA_ARGS__) ) \
-      (pad)                       \
-      ( _FIRST(__VA_ARGS__) )  
-
-  #define _REST(a ,...) __VA_ARGS__
-  #define REST(...)\
-    IF \
-      ( NOT_EXISTS(__VA_ARGS__) ) \
-      ()                          \
-      ( _REST(__VA_ARGS__) )  
-
-  // _SECOND defined in the logic section
-  #define SECOND(pad ,...) \
-    IF \
-      ( NOT_EXISTS(__VA_ARGS__) ) \
-      (pad)                       \
-      ( _SECOND(__VA_ARGS__ ,pad) )  
-
-  #define _THIRD(a ,b ,c ,...) c
-  #define THIRD(pad ,...) \
-    IF \
-      ( NOT_EXISTS(__VA_ARGS__) ) \
-      (pad)                       \
-      ( _THIRD(__VA_ARGS__ ,pad, pad) )  
-
-#endif
diff --git a/developer/example_cpp/cpp_ext_1.c b/developer/example_cpp/cpp_ext_1.c
deleted file mode 100644 (file)
index bc241d7..0000000
+++ /dev/null
@@ -1,90 +0,0 @@
-/*
-These are the recursive extension.
-
-Simple errors can lead to very long error outputs, which might be why
-the cpp designers had obviously intended that recursion would not be possible.
-
-To be added:
-
-LIST_TOO_LONG
-  
-// scanning left to right finds first that exists
-LEFTMOST_EXISTENT 
-
-// scanning left to right finds last that exits
-RIGHTMOST_EXISTENT
-
-DROP_NOT_EXISTS_ALL
-DROP_NOT_EXISTS_LEFT
-DROPE_NOT_EXISTS_RIGHT
-
-#define _CAT(sep,first,...)                              \
-
-*/
-
-#ifndef CPP_EXT_1
-#define CPP_EXT_1
-
-/*===========================================================================
-  Force extra macro expansion (the EVAL trick)
-  This chain of EVAL macros forces the preprocessor to perform many rescans,
-  which is necessary to β€œunroll” recursive macros.
-===========================================================================*/
-//#define EVAL(...)            EVAL1024(__VA_ARGS__)
-#define EVAL(...)            EVAL32(__VA_ARGS__)
-#define EVAL1024(...)        EVAL512(EVAL512(__VA_ARGS__))
-#define EVAL512(...)         EVAL256(EVAL256(__VA_ARGS__))
-#define EVAL256(...)         EVAL128(EVAL128(__VA_ARGS__))
-#define EVAL128(...)         EVAL64(EVAL64(__VA_ARGS__))
-#define EVAL64(...)          EVAL32(EVAL32(__VA_ARGS__))
-#define EVAL32(...)          EVAL16(EVAL16(__VA_ARGS__))
-#define EVAL16(...)          EVAL8(EVAL8(__VA_ARGS__))
-#define EVAL8(...)           EVAL4(EVAL4(__VA_ARGS__))
-#define EVAL4(...)           EVAL2(EVAL2(__VA_ARGS__))
-#define EVAL2(...)           EVAL1(EVAL1(__VA_ARGS__))
-#define EVAL1(...)           __VA_ARGS__
-
-/*===========================================================================
-  Defer macros: these help β€œhide” recursive calls for additional expansion passes.
-===========================================================================*/
-#define NULL_FN()
-#define DEFER1(m)            m NULL_FN()
-#define DEFER2(m)            m NULL_FN NULL_FN()()
-#define DEFER3(m)            m NULL_FN NULL_FN NULL_FN()()()
-#define DEFER4(m)            m NULL_FN NULL_FN NULL_FN NULL_FN()()()()
-
-/*===========================================================================
-  Quantifiers
-===========================================================================*/
-
-#define _FIND(predicate ,...) \
-  IF \
-    ( NOT_EXISTS(__VA_ARGS__) ) \
-    () \
-    (IF \
-      ( predicate(FIRST(__VA_ARGS__)) ) \
-      ( FIRST( ,__VA_ARGS__) )                    \
-      ( DEFER3(_FIND_CONFEDERATE) ()(predicate ,REST(__VA_ARGS__)) )     \
-     )
-#define _FIND_CONFEDERATE() _FIND
-
-// number of evals required depends upon length of not found list prefix
-#define FIND(predicate ,...) EVAL( _FIND(predicate ,__VA_ARGS__) )
-
-#define _FIND_ITEM(item ,...) \
-  IF \
-    ( NOT_EXISTS(__VA_ARGS__) ) \
-    () \
-    (IF \
-      ( EQ(item ,FIRST(__VA_ARGS__)) )             \
-      ( FIRST( ,__VA_ARGS__) )                    \
-      ( DEFER3(_FIND_ITEM_CONFEDERATE) ()(predicate ,REST(__VA_ARGS__)) )     \
-     )
-#define _FIND_ITEM_CONFEDERATE() _FIND_ITEM
-
-// number of evals required depends upon length of not found list prefix
-#define FIND_ITEM(predicate ,...) EVAL( _FIND_ITEM(predicate ,__VA_ARGS__) )
-
-
-
-#endif  
diff --git a/developer/example_cpp/try_1_exists.c b/developer/example_cpp/try_1_exists.c
deleted file mode 100644 (file)
index c2ca07d..0000000
+++ /dev/null
@@ -1,110 +0,0 @@
-#include "../ccπŸ–‰/cpp_ext_0.c"
-
-#define F 1
-#define O1 2
-#define O2 3
-#define B 4
-#define A 5
-#define R 6
-#define D 7
-
-
-// Patch for _EXISTS to succeed on 0
-#define _REWRITE_TWION_0 _REWRITE_TWION
-
-int main(void){
-  printf("try_1_exists\n\n");
-
-  // Constant macros
-  int x COMMA y = 1;  // Tests that COMMA = ,
-  printf("y? %d\n", y);
-  printf("\n");
-
-  // Token paste test
-  int _cat_result = CAT2(CAT3(F ,O1 ,O2) ,CAT4(B ,A ,R ,D));
-  printf("FOOBARD %d\n" ,_cat_result);
-  printf("\n");
-
-  // Selector macros
-  int first = _FIRST(11 ,22 ,33);    // β†’ 11
-  int second = _SECOND(11 ,22 ,33);  // β†’ 22
-  printf("_FIRST(11 ,22 ,33) = %d\n", first);
-  printf("_SECOND(11 ,22 ,33) = %d\n", second);
-  printf("\n");
-
-  // Existence detection
-  int empty = EXISTS_ITEM();         // β†’ 1 (rewrite hits)
-  int empty_0 = EXISTS_ITEM(0);      // β†’ 1 (rewrite hits)
-  int empty_1 = EXISTS_ITEM(1);      // β†’ 0 (no rewrite)
-  int empty_f = EXISTS_ITEM(hello);  // β†’ 0
-
-  printf("EXISTS_ITEM() = %d\n", empty);
-  printf("EXISTS_ITEM(0) = %d\n", empty_0);
-  printf("EXISTS_ITEM(1) = %d\n", empty_1);
-  printf("EXISTS_ITEM(hello) = %d\n", empty_f);
-  printf("\n");
-
-  // Not Existence detection
-  empty = NOT_EXISTS_ITEM();         // β†’ 1 (rewrite hits)
-  empty_0 = NOT_EXISTS_ITEM(0);      // β†’ 1 (rewrite hits)
-  empty_1 = NOT_EXISTS_ITEM(1);      // β†’ 0 (no rewrite)
-  empty_f = NOT_EXISTS_ITEM(hello);  // β†’ 0
-
-  printf("NOT_EXISTS_ITEM() = %d\n", empty);
-  printf("NOT_EXISTS_ITEM(0) = %d\n", empty_0);
-  printf("NOT_EXISTS_ITEM(1) = %d\n", empty_1);
-  printf("NOT_EXISTS_ITEM(hello) = %d\n", empty_f);
-  printf("\n");
-
-
-  //  int empty_10 = EXISTS_ITEM(10,11,12); // illegal call, try it anyway ..compilation error
-  int empty_11 = EXISTS(10,11,12); // this is a legal call
-  int empty_12 = EXISTS(); 
-
-  // printf("EXISTS_ITEM(10,11,12) = %d\n", empty_10);
-  printf("EXISTS(10,11,12) = %d\n", empty_11);
-  printf("EXISTS() = %d\n", empty_12);
-  printf("\n");
-
-  //  int empty_10 = EXISTS_ITEM(10,11,12); // illegal call, try it anyway ..compilation error
-  empty_11 = NOT_EXISTS(10,11,12); // this is a legal call
-  empty_12 = NOT_EXISTS(); 
-
-  // printf("NOT_EXISTS_ITEM(10,11,12) = %d\n", empty_10);
-  printf("NOT_EXISTS(10,11,12) = %d\n", empty_11);
-  printf("NOT_EXISTS() = %d\n", empty_12);
-  printf("\n");
-
-
-  return 0;
-}
-
-/*
-  2025-03-27T12:38:04Z[developer]
-  Thomas-developer@StanleyΒ§/home/Thomas-masu/developer/N/developer/exampleΒ§
-  > gcc try_1_exists.c 
-
-  2025-03-27T12:40:32Z[developer]
-  Thomas-developer@StanleyΒ§/home/Thomas-masu/developer/N/developer/exampleΒ§
-  > ./a.out
-  _CAT(FOO ,BAR) β†’ 12345
-
-  _FIRST(11 ,22 ,33) = 11
-  _SECOND(11 ,22 ,33) = 22
-
-  EXISTS_ITEM() = 0
-  EXISTS_ITEM(0) = 1
-  EXISTS_ITEM(1) = 1
-  EXISTS_ITEM(hello) = 1
-
-  NOT_EXISTS_ITEM() = 1
-  NOT_EXISTS_ITEM(0) = 0
-  NOT_EXISTS_ITEM(1) = 0
-  NOT_EXISTS_ITEM(hello) = 0
-
-  EXISTS(10,11,12) = 1
-  EXISTS() = 0
-
-  NOT_EXISTS(10,11,12) = 0
-  NOT_EXISTS() = 1
-*/
diff --git a/developer/example_cpp/try_2_connectors.c b/developer/example_cpp/try_2_connectors.c
deleted file mode 100644 (file)
index 98078f1..0000000
+++ /dev/null
@@ -1,200 +0,0 @@
-#include "../ccπŸ–‰/cpp_ext_0.c"
-
-int main(void){
-
-  //--------------------------------------------------------------------------
-  // Existence Checks (sanity anchor)
-  //--------------------------------------------------------------------------
-
-  #define x0 
-  SHOW(  EXISTS_ITEM(x0) );       // β†’ 0 (assumed undefined)
-  SHOW(  NOT_EXISTS_ITEM(x0) );   // β†’ 1
-  printf("\n");
-
-  SHOW(  MATCH(x0) );
-  SHOW(  NOT_MATCH(x0) );
-  printf("\n");
-
-  //--------------------------------------------------------------------------
-  // Primitive Connectors
-  //--------------------------------------------------------------------------
-
-  SHOW( _NOT(0) );  // _RWR_NOT_0 is defined β†’ MATCH β†’ 1
-  SHOW( _NOT(1) );  // no rule β†’ MATCH fails β†’ 0
-  printf("\n");
-
-  SHOW( _AND(0 ,0) );  // rule defined β†’ MATCH β†’ 1
-  SHOW( _AND(1 ,0) );  // rule defined β†’ MATCH β†’ 1
-  SHOW( _AND(0 ,1) );  // rule defined β†’ MATCH β†’ 1
-  SHOW( _AND(1 ,1) );  // rule defined β†’ MATCH β†’ 1
-  SHOW( _AND(1 ,x) );  // not legal args, but worked, rule missing β†’ MATCH fails β†’ 0
-  printf("\n");
-
-  SHOW( _OR(0 ,0) );   // rule defined β†’ NOT_MATCH β†’ 0
-  SHOW( _OR(0 ,1) );   // rule missing β†’ NOT_MATCH β†’ 1
-  SHOW( _OR(1 ,0) );   // rule missing β†’ NOT_MATCH β†’ 1
-  SHOW( _OR(1 ,1) );   // rule missing β†’ NOT_MATCH β†’ 1
-  printf("\n");
-
-  //--------------------------------------------------------------------------
-  // Logical Connectors (BOOL + AND/OR/NOT)
-  //--------------------------------------------------------------------------
-
-  printf("x0 is a macro with an empty definition");
-
-  SHOW( _BOOL(0) );       // 0
-  SHOW( _BOOL(1) );       // 1
-  SHOW( _BOOL(2) );       //  1 because it exists
-  SHOW( _BOOL(x0) );       // 0 because it does not exit (see the #define at the top)
-  printf("\n");
-
-  SHOW( BOOL(0) );       // _FIRST = 0, EXISTS_ITEM(_FIRST) = 0 β†’ _AND(0 ,1) β†’ 0
-  SHOW( BOOL(1) );       // EXISTS_ITEM(1) = 0 β†’ BOOL = 0
-  SHOW( BOOL(10) );       // EXISTS_ITEM(1) = 0 β†’ BOOL = 0
-  SHOW( BOOL() );       // EXISTS_ITEM(1) = 0 β†’ BOOL = 0
-  SHOW( BOOL(x0) );       // EXISTS_ITEM(1) = 0 β†’ BOOL = 0
-  printf("\n");
-
-  SHOW( NOT(0) );        // BOOL = 0 β†’ NOT(0) = _NOT(0) = 1
-  SHOW( NOT(1) );        // BOOL = 0 β†’ NOT(0) = 1
-  SHOW( NOT() );        // BOOL = 0 β†’ NOT(0) = 1
-  SHOW( NOT(10) );        // BOOL = 0 β†’ NOT(0) = 1
-  printf("\n");
-
-  SHOW( AND(1 ,0) );     // 0
-  SHOW( AND(1 ,1) );     // BOOL(1), BOOL(1) = 0,0 β†’ AND(0 ,0) = _AND(0 ,0) = 1
-  printf("\n");
-
-  SHOW( OR(0 ,0) );      // BOOL(1), BOOL(0) = 0,0 β†’ OR(0 ,0) = _OR(0 ,0) = 0
-  SHOW( OR(1 ,0) );      // BOOL(1), BOOL(0) = 0,0 β†’ OR(0 ,0) = _OR(0 ,0) = 0
-  printf("\n");
-
-  //--------------------------------------------------------------------------
-  // Compound Connectors
-  //--------------------------------------------------------------------------
-
-  // Double NOT
-  SHOW( NOT(NOT(0)) );     // β†’ NOT(1) β†’ _NOT(1) β†’ 0
-  SHOW( NOT(NOT(1)) );     // β†’ NOT(0) β†’ _NOT(0) β†’ 1
-
-  // Triple NOT
-  SHOW( NOT(NOT(NOT(0))) );  // β†’ NOT(0) β†’ _NOT(0) β†’ 1
-  SHOW( NOT(NOT(NOT(1))) );  // β†’ NOT(1) β†’ _NOT(1) β†’ 0
-  printf("\n");
-
-  // Nested AND
-  SHOW( AND(1 ,AND(1 ,0)) );  // AND(1 ,AND(1 ,0)) β†’ AND(1 ,0) β†’ _AND(1 ,0) = 0
-  SHOW( AND(1 ,AND(1 ,1)) );  // β†’ AND(1 ,1) β†’ _AND(1 ,1) = 1
-  printf("\n");
-
-  // Nested OR
-  SHOW( OR(0 ,OR(0 ,1)) );    // β†’ OR(0 ,1) β†’ _OR(0 ,1) = 1
-  SHOW( OR(0 ,OR(0 ,0)) );    // β†’ OR(0 ,0) β†’ _OR(0 ,0) = 0
-  printf("\n");
-
-  // Mixed nesting
-  SHOW( AND(NOT(0) ,1) );     // β†’ AND(1 ,1) β†’ _AND(1 ,1) = 1
-  SHOW( AND(NOT(1) ,1) );     // β†’ AND(0 ,1) β†’ _AND(0 ,1) = 0
-  SHOW( OR(NOT(1) ,1) );      // β†’ OR(0 ,1) β†’ _OR(0 ,1) = 1
-  SHOW( OR(NOT(0) ,0) );      // β†’ OR(1 ,0) β†’ _OR(1 ,0) = 1
-  printf("\n");
-
-  // Deep mix
-  SHOW( NOT(AND(1 ,NOT(1))) );  // AND(1 ,0) = _AND(1 ,0) = 0 β†’ NOT(0) = _NOT(0) = 1
-  SHOW( NOT(OR(0 ,NOT(0))) );   // OR(0 ,1) = _OR(0 ,1) = 1 β†’ NOT(1) = _NOT(1) = 0
-  printf("\n");
-
-  // Asymmetric nesting
-  SHOW( AND(OR(0 ,1) ,AND(1 ,1)) ); // OR(0 ,1) = 1, AND(1 ,1) = 1 β†’ AND(1 ,1) = 1
-  SHOW( OR(AND(1 ,0) ,AND(1 ,1)) ); // AND(1 ,0) = 0, AND(1 ,1) = 1 β†’ OR(0 ,1) = 1
-  printf("\n");
-
-  return 0;
-}
-/*
-  2025-03-27T12:59:39Z[developer]
-  Thomas-developer@StanleyΒ§/home/Thomas-masu/developer/N/developer/exampleΒ§
-  > gcc try_2_connectors.c 
-
-  2025-03-27T13:00:11Z[developer]
-  Thomas-developer@StanleyΒ§/home/Thomas-masu/developer/N/developer/exampleΒ§
-  > ./a.out
-  EXISTS_ITEM(x0) --> 0
-  NOT_EXISTS_ITEM(x0) --> 1
-
-  MATCH(x0) --> MATCH()
-  NOT_MATCH(x0) --> NOT_MATCH()
-
-  _NOT(0) --> 1
-  _NOT(1) --> 0
-
-  _AND(0 ,0) --> 0
-  _AND(1 ,0) --> 0
-  _AND(0 ,1) --> 0
-  _AND(1 ,1) --> 1
-  _AND(1 ,x) --> 0
-
-  _OR(0 ,0) --> 0
-  _OR(0 ,1) --> 1
-  _OR(1 ,0) --> 1
-  _OR(1 ,1) --> 1
-
-  _EQ(0 ,0) --> 1
-  _EQ(1 ,1) --> 1
-  _EQ(0 ,1) --> 0
-  _EQ(x ,x) --> 0
-
-  _NOT_EQ(0 ,1) --> 1
-  _NOT_EQ(0 ,0) --> 0
-
-  _BOOL_2(0) --> 0
-  _BOOL_2(1) --> 1
-  _BOOL_2(2) --> 1
-  _BOOL_2(x0) --> 0
-
-  BOOL(0) --> 0
-  BOOL(1) --> 1
-  BOOL(10) --> 1
-  BOOL() --> 0
-  BOOL(x0) --> 0
-
-  NOT(0) --> 1
-  NOT(1) --> 0
-  NOT() --> 1
-  NOT(10) --> 0
-
-  AND(1 ,0) --> 0
-  AND(1 ,1) --> 1
-
-  OR(0 ,0) --> 0
-  OR(1 ,0) --> 1
-
-  NOT(NOT(0)) --> 0
-  NOT(NOT(1)) --> 1
-  NOT(NOT(NOT(0))) --> 1
-  NOT(NOT(NOT(1))) --> 0
-
-  AND(1 ,AND(1 ,0)) --> 0
-  AND(1 ,AND(1 ,1)) --> 1
-
-  OR(0 ,OR(0 ,1)) --> 1
-  OR(0 ,OR(0 ,0)) --> 0
-
-  AND(NOT(0) ,1) --> 1
-  AND(NOT(1) ,1) --> 0
-  OR(NOT(1) ,1) --> 1
-  OR(NOT(0) ,0) --> 1
-
-  NOT(AND(1 ,NOT(1))) --> 1
-  NOT(OR(0 ,NOT(0))) --> 0
-
-  AND(OR(0 ,1) ,AND(1 ,1)) --> 1
-  OR(AND(1 ,0) ,AND(1 ,1)) --> 1
-
-
-  2025-03-27T13:00:12Z[developer]
-  Thomas-developer@StanleyΒ§/home/Thomas-masu/developer/N/developer/exampleΒ§
-  >
-*/
-
-  
diff --git a/developer/example_cpp/try_3_eq.c b/developer/example_cpp/try_3_eq.c
deleted file mode 100644 (file)
index c388f03..0000000
+++ /dev/null
@@ -1,55 +0,0 @@
-#include "../ccπŸ–‰/cpp_ext_0.c"
-
-int main(void){
-
-  //---------------------------------------------------------------------------
-  // EQ Tests β€” identity and mismatch
-  //---------------------------------------------------------------------------
-
-  SHOW(EQ(0 ,0));      // Expected β†’ 1
-  SHOW(EQ(1 ,1));      // Expected β†’ 1
-  SHOW(EQ(0 ,1));      // Expected β†’ 0
-  SHOW(EQ(1 ,0));      // Expected β†’ 0
-
-  SHOW(EQ(x ,x));      // Expected β†’ 0 (no _RWREQ__x__oo__x defined)
-  SHOW(EQ(x ,y));      // Expected β†’ 0
-
-  //---------------------------------------------------------------------------
-  // NOTEQ Tests β€” inverse behavior
-  //---------------------------------------------------------------------------
-
-  SHOW(NOT_EQ(0 ,0));  // Expected β†’ 0 (because EQ β†’ 1, so EXISTS β†’ 0)
-  SHOW(NOT_EQ(1 ,1));  // Expected β†’ 0
-  SHOW(NOT_EQ(0 ,1));  // Expected β†’ 1
-  SHOW(NOT_EQ(1 ,0));  // Expected β†’ 1
-
-  SHOW(NOT_EQ(x ,x));  // Expected β†’ 1 (EQ not defined β†’ NOTEQ = 1)
-  SHOW(NOT_EQ(x ,y));  // Expected β†’ 1
-
-  //---------------------------------------------------------------------------
-  // Mixed cases with macros
-  //---------------------------------------------------------------------------
-
-  #define XSYM 0
-  #define YSYM 1
-
-  SHOW(EQ(XSYM ,XSYM));      // Expected β†’ 1 (0,0)
-  SHOW(EQ(XSYM ,YSYM));      // Expected β†’ 0 (0,1)
-  SHOW(NOT_EQ(XSYM ,YSYM));  // Expected β†’ 1
-
-  SHOW(EQ(XSYM ,0));         // Expected β†’ 1
-  SHOW(EQ(XSYM ,1));         // Expected β†’ 0
-
-  SHOW(NOT_EQ(YSYM ,0));     // Expected β†’ 1
-  SHOW(NOT_EQ(YSYM ,1));     // Expected β†’ 0
-
-  //---------------------------------------------------------------------------
-  // Edge case: undefined symbol
-  //---------------------------------------------------------------------------
-
-  SHOW(EQ(z ,z));        // Expected β†’ 0
-  SHOW(NOT_EQ(z ,z));    // Expected β†’ 1
-
-  printf("\n");
-  return 0;
-}
diff --git a/developer/example_cpp/try_4_if.c b/developer/example_cpp/try_4_if.c
deleted file mode 100644 (file)
index 4d9d3ae..0000000
+++ /dev/null
@@ -1,62 +0,0 @@
-#include "../ccπŸ–‰/cpp_ext_0.c"
-
-int main(void){
-
-  //---------------------------------------------------------------------------
-  // Basic boolean cases
-  //---------------------------------------------------------------------------
-
-  SHOW(IF_ELSE(1)(yes)(no)); 
-  SHOW(IF_ELSE(0)(yes)(no));        // β†’ no
-  printf("\n");
-
-  //---------------------------------------------------------------------------
-  // Symbolic identifiers
-  //---------------------------------------------------------------------------
-  SHOW(IF_ELSE(TRUE)(ok)(fail));    // β†’ ok
-  SHOW(IF_ELSE(FALSE)(ok)(fail));   // β†’ fail
-  SHOW(IF_ELSE(foo)(alpha)(omega)); // β†’ omega (foo is undefined)
-  printf("\n");
-
-  //---------------------------------------------------------------------------
-  // Logic expressions
-  //---------------------------------------------------------------------------
-  SHOW(IF_ELSE(AND(1 ,1))(pass)(fail));  // β†’ pass
-  SHOW(IF_ELSE(OR(0 ,0))(yes)(no));      // β†’ no
-  SHOW(IF_ELSE(NOT(0))(on)(off));        // β†’ on
-  printf("\n");
-
-  //---------------------------------------------------------------------------
-  // Code-like output
-  //---------------------------------------------------------------------------
-  SHOW(IF_ELSE(1)(int x = 1;)(int x = 2;));  // β†’ int x = 1;
-  SHOW(IF_ELSE(0)(int x = 1;)(int x = 2;));  // β†’ int x = 2;
-  printf("\n");
-
-  //---------------------------------------------------------------------------
-  // Comma usage in true/false branches
-  //---------------------------------------------------------------------------
-  SHOW(IF_ELSE(1)(a ,b ,c)(x ,y ,z));  // β†’ a ,b ,c
-  SHOW(IF_ELSE(0)(a ,b ,c)(x ,y ,z));  // β†’ x ,y ,z
-  printf("\n");
-
-  //---------------------------------------------------------------------------
-  // Empty condition
-  //---------------------------------------------------------------------------
-  SHOW(IF_ELSE()(true)(false));       // β†’ false (BOOL() = 0)
-  printf("\n");
-
-  //---------------------------------------------------------------------------
-  // Nested IF_ELSE
-  //---------------------------------------------------------------------------
-  SHOW(
-    IF_ELSE(AND(1 ,1))(
-      IF_ELSE(0)(inner_true)(inner_false)
-    )(
-      outer_false
-    )
-  ); // β†’ inner_false
-  printf("\n");
-
-  return 0;
-}
diff --git a/developer/example_cpp/try_5_access.c b/developer/example_cpp/try_5_access.c
deleted file mode 100644 (file)
index aee6c94..0000000
+++ /dev/null
@@ -1,46 +0,0 @@
-#include "../ccπŸ–‰/cpp_ext_0.c"
-
-int main(void){
-
-  //---------------------------------------------------------------------------
-  // FIRST
-  //---------------------------------------------------------------------------
-
-  SHOW(FIRST(foo));                 // β†’ foo         (only pad, no args)
-  SHOW(FIRST(foo ,a));             // β†’ a
-  SHOW(FIRST(foo ,a ,b ,c));       // β†’ a
-  printf("\n");
-
-  //---------------------------------------------------------------------------
-  // REST
-  //---------------------------------------------------------------------------
-
-  SHOW(REST());                    // β†’ (empty)
-  SHOW(REST(a));                  // β†’ (empty)
-  SHOW(REST(a ,b));               // β†’ b
-  SHOW(REST(a ,b ,c ,d));         // β†’ b ,c ,d
-  printf("\n");
-
-  //---------------------------------------------------------------------------
-  // SECOND
-  //---------------------------------------------------------------------------
-
-  SHOW(SECOND(X));                // β†’ X         (only pad)
-  SHOW(SECOND(X ,a));             // β†’ X         (only one arg, fallback to pad)
-  SHOW(SECOND(X ,a ,b));          // β†’ b
-  SHOW(SECOND(X ,a ,b ,c));       // β†’ b
-  printf("\n");
-
-  //---------------------------------------------------------------------------
-  // THIRD
-  //---------------------------------------------------------------------------
-
-  SHOW(THIRD(X));                 // β†’ X         (pad returned)
-  SHOW(THIRD(X ,a));              // β†’ X
-  SHOW(THIRD(X ,a ,b));           // β†’ X
-  SHOW(THIRD(X ,a ,b ,c));        // β†’ c
-  SHOW(THIRD(X ,a ,b ,c ,d));     // β†’ c
-  printf("\n");
-
-  return 0;
-}
diff --git a/developer/example_cpp/try_6_list.c b/developer/example_cpp/try_6_list.c
deleted file mode 100644 (file)
index 75506ec..0000000
+++ /dev/null
@@ -1,60 +0,0 @@
-#include "../ccπŸ–‰/cpp_ext_0.c"
-#include "../ccπŸ–‰/cpp_ext_1.c"
-
-#define LIST Integer ,Float ,Char ,Void 
-
-// register equality
-#define EQ__Integer__oo__Integer
-#define EQ__Float__oo__Float
-#define EQ__Char__oo__Char
-#define EQ__Void__oo__Void
-
-// make predicates
-#define IS_Integer(x) EQ(x ,Integer)
-#define IS_Float(x)   EQ(x ,Float)
-#define IS_Missing(x) EQ(x ,Missing)
-#define IS_Char(x)    EQ(x ,Char)
-#define IS_Void(x)    EQ(x ,Void)
-
-int main(void){
-
-  SHOW(IS_Char(Integer));
-  SHOW(IS_Char(Char));
-  printf("\n");
-
-  SHOW( FIND(IS_Char ,) );
-  SHOW( FIND(IS_Char ,Char) ); 
-  SHOW( FIND(IS_Char ,Integer) ); 
-  printf("\n");
-
-  SHOW( FIND(IS_Char ,Integer ,Void) ); 
-  SHOW( FIND(IS_Void ,Integer ,Void) ); 
-  printf("\n");
-
-  SHOW( FIND(IS_Integer ,LIST) ); 
-  SHOW( FIND(IS_Float ,LIST) ); 
-  SHOW( FIND(IS_Missing ,LIST) ); 
-  SHOW( FIND(IS_Char ,LIST) ); 
-  SHOW( FIND(IS_Void ,LIST) ); 
-  SHOW( FIND(IS_big ,LIST) ); // literal 'IS_big' will be seen as true
-  printf("\n");
-
-  SHOW( FIND_ITEM(Char ,) );
-  SHOW( FIND_ITEM(Char ,Char) );  
-  SHOW( FIND_ITEM(Char ,Integer) );  
-  printf("\n");
-
-  SHOW( FIND_ITEM(Char ,Integer ,Void) ); 
-  SHOW( FIND_ITEM(Void ,Integer ,Void) ); 
-  printf("\n");
-
-  SHOW( FIND_ITEM(Integer ,LIST) ); 
-  SHOW( FIND_ITEM(Float ,LIST) ); 
-  SHOW( FIND_ITEM(Missing ,LIST) ); 
-  SHOW( FIND_ITEM(Char ,LIST) ); 
-  SHOW( FIND_ITEM(Void ,LIST) ); 
-  SHOW( FIND_ITEM(big ,LIST) ); 
-  printf("\n");
-
-  return 0;
-}
diff --git a/developer/example_cpp/try_ext_0.c b/developer/example_cpp/try_ext_0.c
new file mode 100644 (file)
index 0000000..127f3f0
--- /dev/null
@@ -0,0 +1,116 @@
+#include "../ccπŸ–‰/cpp_ext_0.c"
+
+int main(void){
+  //--------------------------------------------------------------------------
+  // Existence Checks (sanity anchor)
+  //--------------------------------------------------------------------------
+
+  SHOW( _FIRST(1) ); 
+  SHOW( _FIRST() );  // returns nothing, as empty args are permitted
+  SHOW( _SECOND(1,2) );
+  // SHOW( _SECOND(1) ); // fails, as _SECOND needs at least two args
+  SHOW( _SECOND(1,) ); // returns nothing, as empty args arg slots are permitted
+  printf("\n");
+
+  SHOW( RETURN_NOTHING() );
+  printf("\n");
+
+  SHOW( _OR() );
+  SHOW( _OR(1) );
+  SHOW( _OR(1,2,3) );
+  printf("\n");
+
+  #define T(x) 7
+  SHOW( T(x) );
+
+  SHOW( _NOT_ITEM() );
+  SHOW( _NOT_ITEM(1) );
+  SHOW( _NOT_ITEM(T(x)) );
+  // SHOW( NOT_ITEM(1,2,3) ); // compiler error parameter arity mismatch
+  printf("\n");
+
+  SHOW( NOT() );
+  SHOW( NOT(1) );
+  SHOW( NOT(T(x)) );
+  SHOW( NOT(1,2,3) );
+  printf("\n");
+
+  SHOW( BOOL() );
+  SHOW( CAT2(_IF_ ,BOOL()) );
+  printf("\n");
+
+  SHOW( TO_1_OR_0() );
+  SHOW( TO_1_OR_0(1) );
+  SHOW( TO_1_OR_0(x) );
+  SHOW( TO_1_OR_0(1.2.3) );
+  printf("\n");
+
+  //--------------------------------------------------------------------------
+  // EXISTS
+  //--------------------------------------------------------------------------
+
+  SHOW( EXISTS() );            // false β†’ Ξ΅
+  SHOW( EXISTS(0) );           // true β†’ 1
+  SHOW( EXISTS(x,y,z) );       // true β†’ 1
+  printf("\n");
+
+  //--------------------------------------------------------------------------
+  // Logic Connectors
+  //--------------------------------------------------------------------------
+
+  SHOW( LEQ2( ,    ) );  // () implies () β†’ 1
+  SHOW( LEQ2( ,  1 ) );  // () implies 1 β†’ 1
+  SHOW( LEQ2( 1,    ) ); // 1  implies () β†’ () (fail)
+  SHOW( LEQ2( 1,  0 ) ); // 1  implies 0 β†’ 0 (still true!)
+  printf("\n");
+
+  SHOW( XOR2( ,    ) );  // both false β†’ false
+  SHOW( XOR2( ,  0 ) );  // one true β†’ true
+  SHOW( XOR2( 0,  0 ) ); // both true β†’ false
+  printf("\n");
+
+  SHOW( AND2( ,  0 ) );  // one false β†’ false
+  SHOW( AND2( 0,  1 ) ); // both true β†’ true
+  printf("\n");
+
+  SHOW( OR2( ,    ) );   // both false β†’ false
+  SHOW( OR2( ,  0 ) );   // one true β†’ true
+  printf("\n");
+
+  //--------------------------------------------------------------------------
+  // Registered Equivalence
+  //--------------------------------------------------------------------------
+
+  #define EQ__APPLE__oo__APPLE
+  #define EQ__PEAR__oo__PEAR
+    
+  SHOW( EQ(APPLE ,APPLE) );
+  SHOW( EQ(APPLE ,PEAR) );
+  SHOW( EQ(PEAR ,PEAR) );
+  SHOW( EQ(,) );
+  SHOW( EQ(,PEAR) );
+  SHOW( EQ(PEAR ,) );
+  printf("\n");
+
+ //--------------------------------------------------------------------------
+  // BOOLEAN
+  //--------------------------------------------------------------------------
+
+  SHOW( BOOLEAN() );           // false β†’ 0
+  SHOW( BOOLEAN(0) );          // true β†’ 1
+  SHOW( BOOLEAN(foo) );        // true β†’ 1
+  SHOW( BOOLEAN(1,2,3) );      // true β†’ 1
+  printf("\n");
+
+  //--------------------------------------------------------------------------
+  // Remainder of a list
+  //--------------------------------------------------------------------------
+
+  SHOW(REST());
+  SHOW(REST(1));
+  SHOW(REST(1,2));
+  SHOW(REST(1,2,3));
+
+
+}
+  
diff --git a/developer/example_cpp/try_ext_1.c b/developer/example_cpp/try_ext_1.c
new file mode 100644 (file)
index 0000000..8e87532
--- /dev/null
@@ -0,0 +1,106 @@
+#include "../ccπŸ–‰/cpp_ext_0.c"
+#include "../ccπŸ–‰/cpp_ext_1.c"
+
+int main(void){
+
+  //--------------------------------------------------------------------------
+  // EVAL and DEFER sanity check (no visual outputβ€”verifies expansion only)
+  //--------------------------------------------------------------------------
+
+  #define PLUS_ONE(x) x + 1
+  #define EXAMPLE_CHAIN(x) PLUS_ONE(PLUS_ONE(x))
+  SHOW( EVAL(EXAMPLE_CHAIN(3)) ); // -> 3 + 1 + 1
+  printf("\n");
+
+  //--------------------------------------------------------------------------
+  // FIND: returns first matching item from list
+  //--------------------------------------------------------------------------
+
+  #define EQ__A__oo__A
+  #define EQ__B__oo__B
+  #define EQ__C__oo__C
+  #define EQ__D__oo__D
+
+  #define EQ__X__oo__X
+  #define EQ__Y__oo__Y
+  #define EQ__Z__oo__Z
+
+  #define IS_X(a) EQ(a ,X) // IS makes use of the EQ template for X
+
+  SHOW( FIND(IS_X ,A ,B ,X ,Y ,Z) ); // β†’ X
+  SHOW( FIND(IS_X ,A ,B ,C ,D) );    // β†’ Ξ΅
+  printf("\n");
+
+  //--------------------------------------------------------------------------
+  // HAS_ITEM: returns 1 if item found
+  //    HAS requires the EQ templates to be set for each case.
+  //--------------------------------------------------------------------------
+
+  SHOW( EQ(A ,B) );
+  SHOW( EQ(B ,B) );
+  printf("\n");
+
+  SHOW( HAS_ITEM(C ,A ,B ,C ,D) );   // β†’ 1
+  SHOW( HAS_ITEM(Z ,A ,B ,C ,D) );   // β†’ Ξ΅
+  printf("\n");
+
+
+  //--------------------------------------------------------------------------
+  // WHILE: stops when predicate fails
+  //--------------------------------------------------------------------------
+
+  #define NON_Z(x) NOT(EQ(x ,Z)) // makes uses of the EQ template for Z
+
+  SHOW( WHILE(NON_Z ,A ,B ,C ,Z ,D ,E) ); // β†’ Ξ΅ (stops at Z)
+  SHOW( WHILE(NON_Z ,A ,B ,C) );          // β†’ 1 (all pass)
+  printf("\n");
+
+  SHOW(EXISTS());
+  SHOW(EXISTS(0));
+  SHOW(EXISTS(1));
+  SHOW(EXISTS(X));
+  SHOW( WHILE(EXISTS ,1 ,X , ));
+  SHOW( WHILE(EXISTS ,1 ,  ,X ,0));
+  SHOW( WHILE(EXISTS ,1 ,X ,0));
+
+  printf("\n");
+
+
+  //--------------------------------------------------------------------------
+  // LAST: returns final item of list
+  //--------------------------------------------------------------------------
+
+  SHOW( LAST(A ,B ,C ,D ,Z) );  // β†’ Z
+  SHOW( LAST(A ,B ,) );  // β†’ 
+  SHOW( LAST() );              // β†’ Ξ΅
+  printf("\n");
+
+  //--------------------------------------------------------------------------
+  // CAT: join items with a separator
+  //--------------------------------------------------------------------------
+
+  //  SHOW( CAT( ;, A ,B ,C ,D ,Z) );  // β†’ Z
+  SHOW( CAT(,A ,B ,C) );  // β†’ 
+  SHOW( CAT( COMMA, A ,B ,C ,D ,Z) );  // β†’ Z
+  SHOW( CAT(,A ,B ,) );  // β†’ 
+  SHOW( CAT(,1) );  
+  SHOW( CAT(,) );              // β†’ Ξ΅
+  printf("\n");
+
+  //--------------------------------------------------------------------------
+  // AND: true if all items are true (non-empty)
+  //--------------------------------------------------------------------------
+#if 0
+  SHOW( AND(1 ,X ,0) );        // β†’ 1
+  SHOW( AND(1 ,X ,) );       // β†’ Ξ΅
+  printf("\n");
+
+  //--------------------------------------------------------------------------
+  // OR: true if any item is true (non-empty)
+  //--------------------------------------------------------------------------
+
+  SHOW( OR( , , ,X) );         // β†’ 1
+  SHOW( OR( , , ,) );          // β†’ Ξ΅
+  printf("\n");
+#endif
+}