https://github.com/phenax/react-is-a-programming-language
Proving react is a turing-complete programming language by making it do things it wasn't meant to do
https://github.com/phenax/react-is-a-programming-language
react reactjs turing-complete
Last synced: 3 months ago
JSON representation
Proving react is a turing-complete programming language by making it do things it wasn't meant to do
- Host: GitHub
- URL: https://github.com/phenax/react-is-a-programming-language
- Owner: phenax
- License: mit
- Created: 2024-05-05T13:20:59.000Z (over 1 year ago)
- Default Branch: main
- Last Pushed: 2024-05-10T15:08:09.000Z (over 1 year ago)
- Last Synced: 2024-11-16T04:38:50.590Z (about 1 year ago)
- Topics: react, reactjs, turing-complete
- Language: TypeScript
- Homepage:
- Size: 164 KB
- Stars: 18
- Watchers: 1
- Forks: 0
- Open Issues: 0
-
Metadata Files:
- Readme: README.md
- License: LICENSE
Awesome Lists containing this project
README
# Reactjs is a turing complete programming language
Note: Uses react canary (19)
Our [App.tsx](./src/App.tsx) here calculates factorial of a number, fibonacci sequence and does a bit of arithmetics but it does all that using react (not JS). What I mean by that is:
- No function recursion
- No loops
- No if-else/`?:` ternaries/`&& ||` ternaries
- No switch-case
- No arithmetic operators
**So every bit of computation in this repo (as much as possible) is done using react only.**

## Example
Here's how the factorial component looks like:
```tsx
const Factorial: FC = React.memo(({ n }) => {
const [count, setCount] = useState(n);
const [result, setResult] = useState();
useLoop();
return (
<>
Calculating factorial of {n}...
{result}
{numberToNode(count)},
]} />
}>
{([newCount, newResult]) => {
setCount(newCount);
setResult(numberToNode(newResult))
}} />}
>
);
});
const App = () => {
return (
}>
{result => (
5! = {result})}
);
};
```
## How it works
Not that anyone needs this information but here it is anyway...
#### useLoop
Just a forever loop created by updating a state inside a `useEffect` with a dependency on the state itself. (Has a tiny delay to get the render to run reliably)
#### CallElement
Removing some of the noise, the core of what happens looks like this:
```tsx
{computation}}>
{getResultOfComputation}
```
`Suspense` wraps the computation where `AwaitResource` is waiting for some promise to resolve. So react renders the fallback.
`Return` context provides a function inside your computation which is meant to be invoked when the computation is done.
When the function is invoked, it resolves the promise which the `AwaitResource` component is waiting for.
This then renders the `AwaitResource` along with the result of the computation.
#### CallFunction
Just a useEffect that calls the function when rendered.
#### IfElse
Nothing fancy. Renders the first child if the condition is true, otherwise renders the second child.
Index of child picked = `Number(!condition)`
#### Natural numbers
Numbers are represented as react elements.
- `0` is `<>>`
- `1` is `
`
- `2` is `<>>`
- ...
So, the number of the `nat` dom nodes is what represents our number.
- Addition, is a combination of 2 nat react elements that represent natural numbers `<>>`.
- Multiplication is just the react element for the second number repeated the first number of times.
- Decrement removes the `data-type` attribute from one of the nodes. (No subtraction implemented yet but it'd be this multiple times)
Note: `Add` component also doubles as a natural number node to number converter.
> Sort of cheating here by using dom nodes so if anyone knows a way to do arithmetics without the dom, please let me know!
#### EvaluateAll
Just `CallElement` for each react element in the array. Essentially `Promise.all` for react elements.
## How to run it?
Why would you want to do something like that? But if you're sure you want to...
- Clone this thing
- Install dependencies `bun i` (Uses bun because I'm cool like that)
- `bun run dev`
- Open `localhost:5173` in your browser