MoreRSS

site iconThe Practical DeveloperModify

A constructive and inclusive social network for software developers.
Please copy the RSS to your reader, or quickly subscribe to:

Inoreader Feedly Follow Feedbin Local Reader

Rss preview of Blog of The Practical Developer

Red Queen Hypothesis and The Crescendo Jailbreak Attack Explained

2025-11-28 11:30:59

chess_game

It takes all the running you can do, to keep in the same place

When I think about safe guarding LLMs against attacks the paradigm that comes to mind is the Red Queen Hypothesis:

The Red Queen hypothesis in evolutionary biology is a theory that species must constantly adapt, evolve, and proliferate in order to survive while pitted against ever-evolving opposing species.
source

How does a theory from Evolutionary Biology relate to modern day Artificial Intelligence attacks? In the wild, the prey can never fully evolve past the predator’s attacks because as the prey is evolving it’s defenses, the predator is in parallel, evolving strategies to overcome those defenses. So, evolutionary speaking, the prey can never fully out run it’s predator — it can only “keep pace” with the predator (see sub-header above).

Just like a rabbit trying to out run a fox, as safe guards in Artificial Intelligence become more sophisticated, so do the attacks. Which brings us to today’s topic.

Background

LLMs are designed to resist engaging in bad behavior. Jailbreaks attempt to overcome this design and override the programed-benevolence of the LLM. A Jailbreak attempts to move the line of what the LLM can do and what it is willing to do. This is also known as Alignment, which ensures that the LLM goals and outputs are consistent with the human’s intentions and values. Jailbreak attacks exploit vulnerabilities in this alignment to make the model generate harmful, biased, or restricted content. In addition, previous Jailbreak attacks have been single-turn inputs.

Various Jailbreak attacks include:

  • optimization-based jailbreaks: involve adversaries optimizing a suffix to circumvent the model’s safety measures

  • textual inputs: where attackers craft a text input that includes instructions or triggers, often in a one-shot setting
    Tools already exist to block these types of attacks, but what makes the Crescendo method different is it uses a multi-turn conversational inputs that are benign but are intended as an attack.

A New Kind of Attack

As LLMs evolve to become more complex and sophisticated, the attacks also evolve with the LLMs in order to penetrate the newly adapted safeguards. Crescendo builds upon existing Jailbreak attacks, it uses a simple multi-turn conversational method in a benign manner. It starts with a general question to the LLM about the task at hand and then gradually escalates by referencing the model’s replies progressively, which leads to a successful Jailbreak.

Through multiple interactions, Crescendo gradually steers the model to generate harmful content in small, benign steps. Crescendo can be automated using the Crescendomation, a tool that automates the Crescendo jailbreak technique.

How to Protect Against Crescendo

Fortunately, there are ways to circumvent a Crescendo attack:

  • During the LLM training phrase the training data should be pre-filtered to exclude bad content. A drawback with this is that it’s costly and it may be difficult to fully sanitize the training data.

  • Crescendomation could generate datasets across various tasks and use them during alignment to make models more resilient.

  • Having output and input guardrails could also help detect the
    Crescendo jailbreak prompts and model outputs.

In Python

The DeepTeam Python Library has a CrescendoJailbreaking library that can be used to simulate attacks on your LLM. I highly recommend playing around with the library and seeing the Cresendo Method in action.

Conclusion

Protecting your LLM application is the upmost importance for any AI Engineer. It leads to a better user experience while protecting your application. Staying up to date with the newest attacks is part of the job. I hope this article helps to highlight this new type of attack, while providing solutions to circumvent them.

Source:

https://arxiv.org/pdf/2404.01833

https://www.trydeepteam.com/docs/red-teaming-adversarial-attacks-crescendo-jailbreaking

A Complete Guide to MongoDB for Developers (With Code Examples)

2025-11-28 11:08:55

MongoDB has become one of the most popular NoSQL databases in the world. Its flexible schema, JSON-like documents, and developer-friendly ecosystem make it a top choice for modern applications, from small side projects to large-scale enterprise systems.

In this article, you will learn everything you need to know to get started with MongoDB, from installation to CRUD operations, indexes, aggregation, schema design, and best practices.

1. What Is MongoDB?

MongoDB is a NoSQL document database that stores data in BSON (Binary JSON) format. Unlike relational databases, MongoDB does not require predefined schemas, making it more flexible for fast-moving projects and distributed systems.

Key MongoDB Features

  • Schema-less documents
  • Horizontal scaling + sharding
  • High availability with replica sets
  • Rich query language
  • Aggregation framework
  • Integrated indexing
  • Great performance for read/write-heavy applications

2. MongoDB Architecture Overview

MongoDB stores data using the following hierarchy:

MongoDB
 └── Database
      └── Collection
            └── Document
                  └── Field (key/value)

Example:

myDatabase
 └── users (collection)
        └── { name: "Klie", age: 22 } (document)

3. Installing & Connecting to MongoDB

Install MongoDB on your system

You can install MongoDB Community Edition using:

  • Windows: MSI Installer
  • macOS: brew install mongodb-community
  • Linux: Official MongoDB repository

Connect using the Mongo Shell

mongosh

Connect in Node.js (using Mongoose)

import mongoose from "mongoose";

mongoose.connect("mongodb://localhost:27017/mydb")
  .then(() => console.log("MongoDB connected"))
  .catch(err => console.log(err));

4. Basic MongoDB Commands

Show all Databases

show dbs

Create/Use Database

use myDatabase

Show Collections

show collections

5. Creating a Collection & Inserting Documents

Insert One Document

db.users.insertOne({
  name: "Klie",
  age: 24,
  skills: ["C++", "Node.js", "MongoDB"]
});

Insert Many Documents

db.users.insertMany([
  { name: "Farhad", age: 22 },
  { name: "Rahimi", age: 30 }
]);

6. Querying Documents

Find All

db.users.find();

Find with Conditions

db.users.find({ age: { $gt: 20 } });

Find One

db.users.findOne({ name: "Klie" });

7. Updating Documents

Update One

db.users.updateOne(
  { name: "Klie" },
  { $set: { age: 25 } }
);

Update Many

db.users.updateMany(
  { age: { $lt: 30 } },
  { $set: { status: "active" } }
);

8. Deleting Documents

Delete One

db.users.deleteOne({ name: "Farhad" });

Delete Many

db.users.deleteMany({ age: { $gt: 40 } });

9. Indexing in MongoDB

Indexes help improve query performance.

Create Index

db.users.createIndex({ name: 1 });  // 1 = ascending

List Indexes

db.users.getIndexes();

Drop Index

db.users.dropIndex("name_1");

10. The Aggregation Framework

Aggregation is like SQL’s GROUP BY.

Example: Group by age and count users

db.users.aggregate([
  { $group: { _id: "$age", total: { $sum: 1 } } }
]);

Example: Sort by age

db.users.aggregate([
  { $sort: { age: 1 } }
]);

Example: Match + Sort + Limit

db.users.aggregate([
  { $match: { age: { $gt: 20 } } },
  { $sort: { age: -1 } },
  { $limit: 5 }
]);

11. Mongoose (Node.js ODM) Example

User Model

import mongoose from "mongoose";

const userSchema = new mongoose.Schema({
  name: String,
  age: Number,
  skills: [String]
});

const User = mongoose.model("User", userSchema);

export default User;

Create a User

const user = await User.create({
  name: "Klie",
  age: 24,
  skills: ["C++", "Node.js"]
});

Find Users

const users = await User.find({ age: { $gt: 20 } });

12. Schema Design Best Practices

Document-Oriented Mindset

Think in objects, not tables.

Embed when:

  • Data reads together
  • Many-to-one or one-to-few
  • Example: user + address

Reference when:

  • One-to-many with large counts
  • Example: user → 1,000 posts

Avoid deeply nested documents

Keep document size < 16MB.

13. Security Best Practices

  • Always use authentication (mongod --auth)
  • Use environment variables for connection strings
  • Enable role-based access control
  • Use TLS/SSL for production
  • Restrict access with IP whitelisting

14. MongoDB Use Cases

MongoDB is used in:

  • Real-time dashboards
  • E-commerce catalogs
  • Social media apps
  • Mobile backends
  • IoT applications
  • Logging systems
  • Content management platforms

15. Conclusion

MongoDB is a powerful, flexible, and highly scalable NoSQL database that fits modern development workflows very well. Whether you are building an e-commerce platform, a social media system, or a personal project, MongoDB offers simplicity and strong performance.

If you are working with JavaScript, Node.js, or full-stack applications, MongoDB integrates seamlessly and accelerates development time.

The Skill That Separates Average Developers From Great Ones — And It’s Not Coding

2025-11-28 11:07:13

For a long time, I believed software development was all about writing good code clean, scalable, and efficient. I thought if I improved my coding skills, learned new frameworks, and solved more problems, everything else would fall into place.

But as I grew in the field, one realization hit me harder than any bug I ever faced:
Coding isn't the skill that separates average developers from great ones communication is.

Many beginners and even intermediate developers spend years mastering syntax but can't clearly explain their ideas, collaborate smoothly with others, or express their thoughts confidently. And in today's modern software world, that communication gap is a career limiter.

Why Developers Struggle With Communication
Most developers (especially beginners) overlook communication for one simple reason: They think their code will speak for them.
Code doesn't tell your team why you made certain decisions. Code doesn't communicate with designers, product managers, or clients. Code doesn't defend itself in a code review or meeting. YOU do.

This is why good developers sometimes get ignored, overshadowed, or misunderstood not because their code is bad, but because their communication is.

Why Communication Matters More Than You Think
1.Teams depend on it
Modern software engineering is highly collaborative. You're constantly interacting with:
Teammates, designers, project managers, QA testers, and stakeholders. If you can't communicate your ideas clearly, you slow the entire team down.

2. It shows confidence and professionalism
The ability to speak clearly, explain decisions, and ask the right questions instantly makes you look more confident even if you're still a beginner.
Many juniors lose opportunities not because they're unskilled… but because they sound unsure, confused, or quiet.

3. It makes code reviews smoother
Code reviews aren't just about fixing bugs. They're about explaining:
why you chose a certain approach, how your solution works, and what your thinking process was. If you can do this clearly, your team trusts you more.

4. Recruiters notice it instantly
Companies look for more than technical skill. They want people who can: collaborate, explain, documen, and communicate. A developer who writes and speaks clearly feels like someone who can handle responsibility.

A Real Example That Happens Every Day Imagine two junior developers:
Developer A:
Writes excellent, efficient code but struggles to explain their logic. Stays quiet during meetings. Gets nervous when asked questions about their work.

Developer B:
Still learning. Makes mistakes. Not the strongest coder but communicates clearly, explains their thought process, and asks good questions.
Guess who gets trusted more?
Guess who gets chosen for important tasks?
Guess who gets promoted faster?
Always Developer B.

Because teams value clarity and confidence more than silent perfection. How Miscommunication Slows You Down A developer might spend 2 hours writing code… but then 20 minutes fumbling through explanations in a meeting because they never practiced communication. Or they might build something great… only to have it rejected because they misunderstood the requirements all due to poor communication.

Communication failure = project failure. It's that simple.

The Moment I Realized Communication Is a Superpower
At first, I didn't think communication mattered. I believed everything depended on my ability to code well. But the more I learned about the tech industry, the more I understood:
Developers who communicate get more responsibility.
Developers who explain ideas get noticed.
Developers who ask good questions learn faster.
Developers with clear thinking become leaders.

That's when it hit me: Communication is not separate from software engineering it is software engineering. How to Start Improving Your Communication Today Here are simple steps you can begin practicing immediately:
✔ Explain your code to yourself If you can't explain it, you don't understand it enough.
✔ Ask clarifying questions in meetings It shows maturity not weakness.
✔ Write more (posts, notes, documentation) Writing builds the clarity that developers need.
✔ Practice summarizing problems This makes you sound decisive and structured.
✔ Talk through your solutions Even talking to yourself or a mentor helps you sharpen your communication.

Conclusion & Takeaway
Great developers aren't the ones who write the most complex code. They're the ones who can explain, collaborate, and communicate clearly. In a world where teams, remote work, and cross-functional collaboration are the norm, communication isn't a "soft skill." It's a core engineering skill. Good developers code. Great developers communicate. And the earlier you understand this, the faster you grow.

Quality Management Plan Errors That Risk Your Project (And How to Fix Them)

2025-11-28 11:06:58

A Quality Management Plan is often introduced early in project planning, but many teams treat it as a static document instead of a living system for controlling and improving quality. This is where problems begin. A weak or incomplete Quality Management Plan creates gaps that are eventually felt through defects, miscommunication, cost overruns or dissatisfied stakeholders. In project management, these consequences are expensive and difficult to reverse.

A clear and detailed Quality Management Plan helps teams understand what quality means for the project, how it will be measured and how issues will be handled. In this article, you will learn the most common mistakes that weaken a Quality Management Plan, how to fix them, a simple four step method to create one correctly and practical tips you can apply right away. The goal is to help you produce a plan that strengthens your deliverables, supports continuous improvement and aligns with stakeholder expectations.

What Is a Quality Management Plan

A Quality Management Plan is a document in project management that explains how a project will achieve the level of quality expected by stakeholders. It guides the team from the early stages of project planning to the final handoff.

It supports consistency and reduces risks by outlining how work should be performed, checked and improved. Instead of reacting to problems at the end, the plan encourages prevention, early detection and continuous refinement throughout the entire project lifecycle.

What a Quality Management Plan Should Include

Before looking at the mistakes, it helps to revisit what a Quality Management Plan usually contains. A complete plan often includes:

  • A list of project deliverables
  • The processes used to produce these deliverables
  • Quality standards that apply to the project
  • The acceptance criteria that define successful outcomes
  • Customer satisfaction criteria
  • Quality assurance activities
  • Quality control activities
  • Stakeholder expectations
  • Performance thresholds for evaluating results

These elements create structure, predictability and accountability. When several of them are unclear or missing, the project becomes vulnerable to delays, rework, unclear responsibilities and inconsistent expectations.

Common Quality Management Plan Errors

Below are the most frequent errors found in Quality Management Plans. Each error includes a thorough explanation, the impact on project management and detailed steps to correct the issue. For variety and readability, some sections include bullet points, examples and breakdowns.

Error 1: Vague or Unmeasurable Quality Standards

Vague or Unmeasurable Quality Standards

Some plans use language that sounds positive but does not provide measurable direction. Terms like high quality, easy to use or fast performance are too subjective. They cannot be tested or validated because no one knows what threshold defines success.

Why this matters

Vague standards create inconsistent interpretations. One team member may believe the interface is responsive while another may think it still feels slow. Customers may assume a level of polish that the team never planned for. These gaps lead to late stage conflict and rework.

How to fix it

Translate subjective statements into measurable criteria. Examples include:

  • Page load speed under 2.5 seconds
  • Maximum of two minor defects per release
  • Client satisfaction score above 90 percent during acceptance testing
  • Compliance with accessibility WCAG 2.1 guidelines

Specific measurements help the team design tests, evaluate outcomes and agree on what acceptable quality looks like.

Error 2: Ignoring Stakeholder Input During Quality Planning

Ignoring Stakeholder Input During Quality Planning

Quality is not defined by the project team alone. Project stakeholders often have expectations about functionality, appearance, performance, compliance or reliability. When their input is collected once at the beginning but never validated, misalignment grows throughout the project.

Signs this error is happening

  • Stakeholders begin raising concerns late in the project
  • Deliverables pass internal tests but fail acceptance tests
  • Features are technically correct but do not match real-world expectations

Why this matters

Stakeholder dissatisfaction can delay approval, increase negotiation cycles and trigger costly rework. It also weakens trust and makes project governance harder.

How to fix it

  • Hold requirement validation sessions throughout the project
  • Include stakeholder expectations in acceptance criteria
  • Use prototypes or interim deliverables to confirm quality early
  • Update the Quality Management Plan when stakeholder needs change

Blending stakeholder input with project limitations creates a more realistic and achievable definition of quality.

Error 3: Unclear or Missing QA and QC Activities

Quality assurance and quality control support two different parts of the project. Quality assurance focuses on preventing defects through process improvements. Quality control focuses on detecting defects in deliverables. Many plans mix the two or fail to define them at all.

The impact of this mistake

  • Teams skip important checks because no one owns them
  • Testing becomes inconsistent
  • Root causes of issues remain unknown
  • Defects pile up late in the project

How to fix it

Break the activities down clearly.

Quality assurance examples

  • Training sessions for new processes
  • Checklists for design or development steps
  • Process audits
  • Peer reviews

Quality control examples

  • Functional testing
  • Regression testing
  • Inspections of deliverables
  • Acceptance testing procedures

This separation helps the team prevent, detect and correct quality issues systematically.

Error 4: Undefined Roles and Responsibilities

A Quality Management Plan must identify who is responsible for quality activities. When roles are unclear, tasks are either duplicated or forgotten.

Common symptoms

  • Confusion about who should approve a deliverable
  • Delays because no one takes ownership of testing
  • Disagreements about who reports defects
  • Miscommunication during handovers

How to fix it

Assign roles for every quality activity. A RACI-style breakdown works well. It is based on these principles:

  • Responsible
  • Accountable
  • Consulted
  • Informed

This approach removes ambiguity and supports smooth project execution.

Error 5: Weak or Missing Performance Thresholds

Weak or Missing Performance Thresholds

Even when standards appear clear, many Quality Management Plans do not define thresholds for acceptable performance. A deliverable may meet functional requirements but still fail expectations because the allowable range is unclear.

Examples of missing thresholds

  • A report is considered complete, but the client expected a specific accuracy percentage
  • A mobile app passes testing, but performance on older devices is unacceptable
  • A construction project meets the design plan, but tolerances are not defined

How to fix it

Include performance thresholds such as:

  • Minimum pass rates
  • Target error margins
  • Acceptable defect counts
  • Compliance percentages

These thresholds help teams understand exactly when a result is acceptable and when corrective action is needed.

Error 6: Poor Monitoring and Reporting Practices

Poor Monitoring and Reporting Practices

Monitoring quality without a consistent reporting rhythm leads to blind spots. Plans often fail because reporting is informal or irregular. Decisions are then based on incomplete information.

Why this matters

  • Teams discover issues too late
  • Stakeholders lose confidence
  • Quality trends are not visible
  • Continuous improvement becomes difficult

How to fix it

  • Establish a reporting frequency
  • Decide who receives updates
  • Use dashboards or logs to track defects
  • Create escalation criteria for severe issues

Predictable reporting strengthens communication and early intervention.

Error 7: Slow or Missing Corrective Actions

Identifying an issue is only the first step. Many projects struggle because corrective action is not clearly defined or scheduled. Problems are acknowledged but not addressed quickly enough.

Consequences

  • Defects repeat across deliverables
  • Rework accumulates
  • Project timeline expand
  • Quality declines near the end of the project

How to fix it

  • Create a corrective action workflow
  • Document root causes
  • Assign deadlines for fixes
  • Review whether the action prevented recurrence

Corrective action should bring the project back to the quality baseline rather than only patching symptoms.

How to Create a Quality Management Plan in 4 Steps

Below is the four step method from your earlier version, kept intact because it is the most accurate and practical.

Step 1: Plan Development

Identify customer quality objectives through interviews and research. Review legal, environmental, professional and industry standards. Balance customer needs with project constraints. Define performance thresholds and confirm them with customers.

Step 2: Execute the Plan

Carry out tasks according to the approved Quality Management Plan. Maintain communication across teams and document activities. Gather observations for future lessons learned.

Step 3: Perform Quality Checks

Conduct technical reviews, process oversight and verification steps. Compare results with customer quality objectives and report findings at regular intervals. Treat each cycle as an opportunity for continuous improvement.

Step 4: Take Corrective Action

Address anomalies quickly to return the project to its quality baseline. Document changes so improvements can be kept for future projects or updates to the Quality Management Plan.

Example of a Quality Management Plan

Section Example
Project Mobile App Feature Upgrade
Customer Quality Objectives Smooth performance, under 1-second load time, no critical bugs
Industry Standards App Store compliance, basic accessibility, data security
Performance Thresholds 95% test pass rate, maximum two minor defects per release
Execution Notes Weekly sync between development and QA teams, documented test cycles
Quality Checks Code reviews, regression testing, small user group usability tests
Corrective Action Fix defects within 48 hours, adjust workflow if patterns repeat

This Quality Management Plan outlines how a team ensures an upgraded mobile app feature meets customer expectations and industry requirements. It highlights clear performance goals, like fast load times and minimal bugs, and ties them to measurable testing standards.

The plan also defines how quality will be maintained during development, including weekly coordination between teams, structured test cycles, and consistent code reviews. Finally, it sets rules for corrective action so issues are fixed quickly and recurring problems are addressed through workflow improvements.

Practical Tips for a Stronger Quality Management Plan

  • Involve stakeholders throughout the project, not only at the start
  • Convert all quality statements into measurable targets
  • Map QA and QC activities onto the project schedule
  • Use templates and checklists to maintain consistency
  • Keep communication active between technical teams and decision makers
  • Update the plan whenever major requirements shift
  • Document issues and successes to support continuous improvement

Conclusion

A strong Quality Management Plan protects your project from avoidable issues by setting clear standards, defining responsibilities and aligning everyone on what quality truly means. When these elements are missing or vague, even simple tasks can lead to delays, rework and frustrated stakeholders.

By applying the four step method and keeping quality checks consistent, your plan becomes a practical guide that supports better decisions and smoother delivery. With the right approach, quality becomes predictable, customer satisfaction increases and your project has a far stronger chance of success.

Learn more

Billiard Fractals: The Infinite Patterns Hidden in a Rectangle

2025-11-28 11:05:30

Complex systems often appear chaotic or incomprehensible, yet closer examination reveals that such complexity can frequently be reduced to a simple underlying mechanism. By systematically removing layers of emergent behavior, one can uncover a fundamental rule or equation from which the entire system originates.

The Billiard Fractal

While the system described in this article may appear trivial at first glance, the resulting patterns exhibit quasi-fractal behavior that can be analyzed, encoded, and even predicted through symbolic methods. The work presented here was developed independently through direct observation, rather than derived from prior literature.

A useful way to motivate this exploration is by analogy with a common physical phenomenon - wave interference. Consider waves on the surface of a river: a wavefront moves toward the shore, reflects, and overlaps with itself. Do these reflections contain an underlying order? Is it possible to extract structure from the interference?

To investigate this, we simplify the system. Rather than modeling the full wave, we consider only the motion vector - essentially, a ray. We also smooth the “shoreline” and discretize the environment into a rectangular grid. From this setup emerges the core construction of this article.

":)"

The example of waves on the surface of a river serves as a real, intuitive starting point - an accessible physical system that demonstrates how simple rules, such as reflection and interference, can produce complex behavior. It illustrates the central idea: that what appears chaotic often emerges from deterministic structure.

The initial motivation was driven by the conviction that apparent disorder is not randomness, but the result of unresolved or hidden structure. Any system that seems chaotic is governed by rules - its complexity a consequence of perspective, not unpredictability.

To explore this further, attention turned to constructing the simplest possible system that could look chaotic yet remain fully deterministic.

One such system involved a sine wave originating from the corner of a rectangle and reflecting off its boundaries. The nonlinearity of the sine function causes it to intersect itself in complex and unintuitive ways. However, due to limited tools available at the time, the model was simplified even further.

Instead of a sine wave, a straight line was used. The line was made periodic (dashed), and the system was designed to be reproducible using only a pencil and a sheet of graph paper. Despite its simplicity, this construction revealed intricate and structured patterns-forming the foundation of what would later be described as the “billiard fractals.”

Visualizing the Billiard Algorithm

The following sequence illustrates the core mechanism of the discrete billiard system:

Picture

An animated version:

Picture

Output pattern:

Picture

A selection of patterns generated from rectangles with various dimensions:

JavaScript implementation of this algorithm

pattern.js - source code

Fibonacci Numbers and Pattern Refinement

The patterns generated by this system exhibit fractal structure: they are self-similar across scales, recursive in construction, and can be compressed symbolically. As the rectangle dimensions increase following the Fibonacci sequence, the patterns reveal increasingly detailed versions of the same underlying structure.

This refinement process is simple: given rectangle dimensions (m, n), new dimensions are generated by Fibonacci summation. For example, starting with 8×13:

  • 13 + 8 → 21 → becomes 13×21
  • Then 21 + 13 → 34 → becomes 21×34, and so on

Each step increases resolution while preserving the underlying structure.

8×13 13×21 21×34 34×55 55×89
8x13 13x21 21x34 34x55 55x89

"233×377 preview comparison"

The article’s header image corresponds to the 233×377 pattern. Its structure can be directly compared with the earlier 13×21 case.

When constructing these patterns using Fibonacci-based dimensions, we are effectively approximating a rectangle with side lengths in the golden ratio - that is, a ratio approaching (1 : φ). With each step, the approximation improves, and the pattern gains additional structure and resolution.

Although the overall structure of the pattern remains consistent during Fibonacci-based refinement, certain symmetries within the pattern depend on the parity of the rectangle's side lengths. Specifically, when both the width and height are odd integers, the resulting pattern exhibits clear diagonal, horizontal, and vertical symmetry. This occurs because the billiard path, under these conditions, terminates in the corner diagonally opposite from its starting point. In contrast, when one or both sides are even, the path terminates elsewhere, and the resulting pattern loses this precise symmetry - although the underlying recursive structure remains unchanged.

Boundary Analysis and Recursive Symmetry

To understand why the structure persists under Fibonacci expansion, consider cutting a square from the pattern. The boundary behavior reveals that the path (i.e., the “billiard ball”) always returns to its entry point:

Square reflection

Moreover, the path always (except for diagonal cases) crosses an even number of cells. This ensures that the pattern remains consistent across such subdivisions.

Trajectory loop

By recursively separating square regions from the larger pattern, the symbolic seed of the system can be exposed:

Recursive breakdown

Binary Representation and Symbolic Extraction

The path traced by the billiard ball through the grid can be encoded as a binary sequence. As the ball moves from cell to cell, its internal state alternates according to a fixed rule. We can label these alternating states with binary values - for example, assigning 0 to one state and 1 to the other. This produces a binary field that can be visualized directly.

For example:

Dashed path

Binary encoded

The top row of the binary field can be viewed as a symbolic boundary - a compact representation of the billiard system's behavior along a single edge. By studying the structure of the full 2D pattern and recursively extracting square sections from it, we arrive at symbolic generation rules. These rules allow us to reconstruct the boundary sequences using only binary operations.

Two core recursive generators are presented below:

function invers(array) {
    var temp = [];
    for (let i = 0; i < array.length; i++)
        temp[i] = array[i] === 0 ? 1 : 0;
    return temp;
}

function revers(array, s) {
    var temp = [];
    for (let i = 0; i < s; i++)
        temp[i] = array[array.length - i - 1];
    return temp;
}

function sequence(fn, fn1) {
    if (fn1 === 3) return [1];
    fn1 = fn - fn1;
    fn = fn - fn1;
    var array = sequence(fn, fn1);
    var a0 = invers(array);
    var a1 = (fn1 % 2 === 0) ? [1] : [];
    var a2 = revers(array, Math.floor((fn - fn1) / 2));
    return a0.concat(a1, a2);
}

function sequenceFibonacci(iterations) {
    let f0a = [0];
    let f1a = [0];
    for (let i = 0; i < iterations; i++) {
        let f0 = f0a.length;
        let a2 = revers(f1a, f0);
        if (f1a.length % 2 === 0) a2[0] ^= 1;
        f0a = f1a;
        f1a = f1a.concat(a2);
    }
    let array = [];
    for (let i = 0; i < Math.floor(f1a.length / 2); i++)
        array[i] = f1a[i * 2];
    return array;
}

These constructions reproduce the symbolic edges of Fibonacci-based patterns and can be interpreted as recursive encoding schemes derived directly from the observed geometry.

"Toward Generalization"

While the above generators are constructed specifically for Fibonacci-sized rectangles, preliminary experiments suggest that similar structures may emerge for other co-prime pairs. These systems may obey different symbolic transformation rules, but exhibit comparable recursive or compressible traits. A formal generalization of these behaviors remains an open area of exploration.

One of the central challenges that motivated the progression from the original 2013 construction to the deeper analysis in 2019 was the question of irrational proportions: what happens when the rectangle’s side lengths form a truly irrational ratio, such as (1 : φ), rather than an integer-based approximation like 13 : 21?

While recursive generators such as sequence(fn, fn1) accurately reproduced the symbolic boundary sequences for Fibonacci-based rectangles, they were inherently tied to integer dimensions. The challenge was clear: how can one generate the same structures when no exact grid alignment is possible - when the trajectory no longer closes?

This question defines the next stage of the investigation. To answer it, we will analyze the boundary sequences themselves - the so-called fractal sequences - and show how they encode the entire 2D pattern. We will show that these sequences - far from being edge artifacts - contain enough information to deterministically reconstruct the entire 2D pattern. This finding enables a powerful dimensional reduction: the entire billiard system can be expressed as a 1D sequence.

Binary Billiards

We now shift from the dashed-line visualization to a binary representation. Instead of drawing the trajectory, we color the cells the ball passes through, alternating black (0) and white (1) with each step.

Given a rectangle with side lengths
MMM and NNN , the ball is launched from a corner and follows diagonal motion, reflecting off the walls. Each step alternates the internal binary state.

Trajectory

Resulting pattern (coprime)

The reflection rule causes the trajectory to shift by one cell after each bounce. This alternation creates a consistent visual structure.

Binary fill

Reflection rule

When
MMM and NNN are coprime, the trajectory visits every cell exactly once:

Full coverage

JavaScript implementation

binarypattern.js

"Gif"

Gif

JavaScript implementation

binarypattern_point.js

If the dimensions share a common divisor ( gcd(M,N)>1gcd(M, N) > 1gcd(M,N)>1 ), the trajectory terminates at a corner before filling all cells:

Terminating early

In this case, the system is equivalent to a billiard in a reduced rectangle with dimensions ( MGCD\frac{M}{GCD}GCDM , NGCD\frac{N}{GCD}GCDN ):

Reduced case

Boundary Behavior and Symmetry

In the coprime case, the ball crosses every row and column. Notably, each pass between the top and left walls consists of an even number of steps.

Even passes

Even passes 2

From this, we can observe a critical symmetry: the left column contains the inverted bits of the top row, excluding the initial bit.

Boundary inversion

Furthermore, every second bit ( 2n−12_{n-1}2n1 ) in the top sequence is the inverted version of its neighbor ( 2n2_{n}2n ). Therefore, we can discard every second bit and retain full pattern information:

Halved sequence

For example, with dimensions M=21,N=13M=21, N=13M=21,N=13 , the resulting sequence is: 1010010110

This sequence is unique for every coprime pair (M,N)(M, N)(M,N) . It encodes all necessary information about the pattern.

Sequence Interpretation

The trajectory between two reflections from the upper wall is always 2N2N2N cells long. Each such pass begins with a black cell (bit = 0) and ends with a white cell (bit = 1):

Reflection path

More formally:

  • A bit of 1 indicates that the ball arrived from a reflection off the right wall
  • A bit of 0 indicates it came from the left wall

This mapping gives the sequence its meaning. In the diagram below, the trajectory is colored black when moving right and white when moving left:

Direction-colored trajectory

Encoding Rational Division via Billiards

A curious side effect of the billiard construction is that it naturally encodes binary division of two numbers. Specifically, by tracking the direction of the billiard ball’s movement at each wall collision, and sampling this information at exponentially increasing intervals, one can extract the binary digits of a rational fraction.

Let the billiard table have side lengths MMM and NNN , and let the ball bounce between corners. At each collision with the top or bottom wall:

If the ball is moving to the right, record a 0

If moving to the left, record a 1

Then, at every 2n2^n2n -th collision (i.e., 1st, 2nd, 4th, 8th, …), we record the state.

Example: for a table of size M=21,N=13M=21, N=13M=21,N=13 , we obtain:

Picture

1st  (bottom, →): 0  
2nd  (top, ←):    1  
4th  (top, →):    0  
8th  (top, →):    0  
16th (top, ←):    1  
32nd (top, ←):    1  
...

This produces the binary expansion:

0.1001111001111001111…
Which is precisely the binary representation of 1321\frac{13}{21}2113 .

Reconstruction from the Sequence

The full billiard pattern can be reconstructed from this single boundary sequence. Even extrapolation beyond the grid is possible.

Let us begin by placing the bits along the top edge of a square grid of width MMM . Bits are spaced every 2 cells - these are the points where the ball would hit the upper wall:

Bit placement

Then:

  • If the bit is 1, we extend a diagonal to the left
  • If the bit is 0, we extend it to the right

Direction rules

The first bit (bit 0) is treated specially - it begins the pattern:

Zero bit start

The reconstruction produces the exact original pattern:

Reconstructed pattern (animated)

Reconstructed result

JavaScript implementation

visualizer.js

This result shows that the 1D sequence contains complete information about the original 2D billiard pattern.

But we're not done.

From the surface of the river, we reduced the system to a rectangular billiard with a dashed diagonal trajectory. Then we reduced it further - to a binary field generated by alternating internal states. Now, we push the reduction one step further: we collapse the entire 2D billiard into a one-dimensional rule. A symbolic system with no geometry left - only structure.

This is where we begin to uncover the origin of these fractals.

One-dimensional billiards

On the XXX number axis, we take two points: 000 and MMM .

Picture

Moving from one point to another, we measure the distances NNN :

Picture

We marked a point. We continue to measure the distance from this point, maintaining the direction. If we reach point 000 or MMM , we change the direction:

Picture

As you can see in the pictures above, the first point shows the place where the ball touches the bottom wall of the billiard table. We are not interested in this point. We will only mark the points 2kN2kN2kN for k=0,1,2,…k=0,1,2,…k=0,1,2, .

How to mark these points? Let's unfold our billiard table on the XXX axis. Let's mark the points 0,M,2M,3M,…0, M, 2M, 3M,…0,M,2M,3M, . Now, having reached point MMM , we do not change the direction of movement, but continue moving to point 2M2M2M .

Picture

Points that are multiples of MMM divide our axis into segments. We will conditionally mark these segments with ones and zeros (alternating). On the segments marked with zeros, the ball (in rectangular billiards) moves from left to right. On the segments marked with ones, it moves from right to left. Or more simply: the ball moves from left to right if Qk=0Q_k=0Qk=0 , for

Qk=⌊2kNM⌋  (mod  2);k=0,1,2,…Q_k=\lfloor \frac{2kN}{M} \rfloor \; (\textrm{mod} \; 2); \quad k=0,1,2,…Qk=M2kN(mod2);k=0,1,2,

It is easy to see that the point at which the ball touched the upper wall of the billiard table is the remainder of dividing 2kN2kN2kN by MMM . In this case, we don't need to record the movement of the ball in the opposite direction. We take the integer part of dividing 2kN2kN2kN by MMM , if it is even - we calculate the remainder of dividing 2kN2kN2kN by MMM . We divide the resulting remainder by 2 (the distance between adjacent touch points is two cells). This gives us the indices of the array elements that correspond to rightward motion (zeros). All other entries - representing leftward trajectories - are filled with ones.

Sequence length = M2\frac{M}{2}2M .

function sequence(m,n){
    var md=m/2;
    var array=[];
    for(var k=0;k<md;k++) array[k]=1;
    for(var k=0;k<md;k++) if(Math.floor(2*k*n/m)%2==0) array[((2*k*n)%m)/2]=0;
    return array;
}

Now we can build a binary sequence for billiards with any sides MMM and NNN (natural numbers). Some examples:
144x89 (Fibonacci numbers):
010100101101001011010110100101101001010010110101001011010100101

169x70 (Pell numbers):
010101101010010101101010010101101010100101011010101001010110101001010101010010101101010010

233x55 (odd Fibonacci numbers FnF_nFn and Fn−3F_{n-3}Fn3 ):
010010011011011001001101101100100100110110010010011011001001001101101100100110110110010010011011001001001101100100100

This is interesting

Very curious graphs are obtained if you take a billiard table with width M and construct sequences for each N from 0 to M. Then these sequences are stacked.

    var array;
    for(var y=1;y<m;y++){
        array=sequence(m,y);
        for(var x=0;x<array.length;x++){
            if(array[x]==0) context.fillRect (x, y, 1, 1);
        }
    }

Some examples.

M=610 M=611 M=612 M=613 M=614
Picture Picture Picture Picture Picture

JavaScript implementation

sequences.js

We have sequences. How else can we visualize binary sequences? With Turtle graphics.

Turtle graphics

The sequence length determines the complexity of the curve. The more irrational the ratio between M and N, the more non-periodic and fractal - like the structure becomes.

Draw a segment. Then take bits from our sequence one by one. If bit = 1 - rotate the segment relative to the previous one by 60∘60^{\circ}60 (clockwise). If bit = 0 - rotate the segment by −60∘-60^{\circ}60 . The beginning of the next segment is the end of the previous one.

Picture

Take two large enough Fibonacci numbers: F29=514229F_{29}=514229F29=514229 and F28=317811F_{28}=317811F28=317811 . This ensures that the pattern is long enough for the fractal structure to become apparent, but still bounded enough for visualization.

We built the sequence:
0010110100101101001010010110100101101010010110100101101001010010110100101… (257114 symbols plus a zero bit).

Visualize using turtle graphics. The size of the initial segment is 1 pixels (the initial segment is in the lower right corner):

Picture

The next example is Pell numbers.

Pn={0,n=0; 1,n=1; 2Pn−1+Pn−2,n>1. P_n = \begin{cases} 0, & n=0; \ 1, & n=1; \ 2P_{n-1} + P_{n-2}, & n>1. \end{cases} Pn={0,n=0; 1,n=1; 2Pn1+Pn2,n>1.

We take P16=470832P_{16}=470832P16=470832 and P15=195025P_{15}=195025P15=195025 .

The sequence is:
00101001010110101001010101010100101011010100101010110101001010101101 (235415 symbols plus a zero bit).

The size of the initial segment is 1 pixel:

Picture

Another example is the odd Fibonacci numbers FnF_nFn and Fn−3F_{n-3}Fn3 .
Let's take F28=317811F_{28}=317811F28=317811 and F25=75025F_{25}=75025F25=75025 .
The sequence is:
00110110010010011011001001101101100100110110110010011011011001001… (158905 plus a zero bit).
Instead of the angles 60∘60^{\circ}60 and −60∘-60^{\circ}60 , we will use the angles 90∘90^{\circ}90 and −90∘-90^{\circ}90 .
The size of the initial segment is 1 pixels:

Picture

This curve is called "Fibonacci Word Fractal". The Hausdorff dimension for this curve is known:

D=3log⁡Φlog⁡(1+2)=1.6379;Φ=1+52D=3{\frac {\log \Phi }{\log(1+{\sqrt {2}})}}=1.6379; \quad \Phi =\frac {1+{\sqrt {5}}}{2}D=3log(1+2)logΦ=1.6379;Φ=21+5

JavaScript implementation

turtle.js

The problem unsolved yet.

Is it possible to draw a pattern for billiards, the sides of which are incommensurable (one of the sides is an irrational number)? At first glance, the task seems impossible. Trying to solve this problem, we will face a number of questions:

  1. If the sides are incommensurable, we cannot tile the billiards with cells of the same size.
  2. If the sides are incommensurable, the ball will infinitely reflect and will never get into the corner.
  3. Sequences in billiards are not filled in order, but chaotically.

Picture

The first two questions obviously have no solution. But if there were a way to fill the sequence in order, then we could, moving along the sequence from left to right, restore the pattern in the way we used above. And thus see what the pattern looks like in the upper left corner of the billiard table whose sides are incommensurable.

o_O

Let's take a billiard table, the sides of which are equal to the Fibonacci numbers (this trick may not work with other numbers). Let's throw a ball into it and record the number of times the ball touches the upper wall. We'll paint the numbers white if the ball moved from right to left and black if the ball moved from left to right:

Picture

White corresponds to the number one in the sequence, black to zero. Now let's arrange the numbers in order:

Picture

We've got exactly the same sequence of ones and zeros.

21(1), 13(0), 8(1), 26(0), 5(0), 16(1), 18(0), 3(1), 24(1), 10(0), 11(1), 23(0), 2(0), 19(1), 15(0), 6(1), 27(1), 7(0), 14(1), 20(0), 1(1), 22(1), 12(0), 9(1), 25(0), 4(0), 17(1)

1(1), 2(0), 3(1), 4(0), 5(0), 6(1), 7(0), 8(1), 9(1), 10(0), 11(1), 12(0), 13(0), 14(1), 15(0), 16(1), 17(1), 18(0), 19(1), 20(0), 21(1), 22(1), 23(0), 24(1), 25(0), 26(0), 27(1)

"For other numbers"

The origin is the upper left corner. The X axis is the width of the billiard table M. The Y axis is the height of the billiard table N. The numbers for which the sequences match are marked with white dots:

Picture

Numbers for which the sequence is inverted:

Picture

JavaScript implementation:

Picture

The first line is the mouse coordinates, which are used as the width and height of the billiard table.
The second line is the first 100 bits of the sequence obtained through the remainders of the division.
The third line is the first 100 bits of the sequence obtained through the parity of the integer part.

Black color - Visualization of the first sequence using Turtle graphics.
Purple - visualization of the second sequence.

JavaScript implementation

turtle_dynamic.js

In fact, in some cases, we do not need to take the remainder from the division. For Fibonacci numbers, it is enough to check the parity of the integer part of the division of 2kN2kN2kN by MMM :

Qk=⌊2kNM⌋  (mod  2);k=0,1,2,…Q_k=\lfloor \frac{2kN}{M} \rfloor \; (\textrm{mod} \; 2); \quad k=0,1,2,…Qk=M2kN(mod2);k=0,1,2,

In the numerator we have FnF_{n}Fn . In the denominator - Fn+1F_{n+1}Fn+1 .

As is known:

lim⁡n→∞FnFn+1=1Φ\lim_{n\to\infty} \frac{F_n}{F_{n+1}}= \frac{1}{\Phi}limnFn+1Fn=Φ1

This gives us a bridge: rational billiards ( FnF_{n}Fn , Fn+1F_{n+1}Fn+1 ) converge toward an irrational limit - Φ\PhiΦ - allowing us to define an infinite symbolic sequence.

Φ\PhiΦ is the Golden Ratio. An irrational number. Now we can write our formula as:

Qk=⌊2kΦ⌋  (mod  2);k=0,1,2,…Q_k=\lfloor \frac{2k}{\Phi} \rfloor \; (\textrm{mod} \; 2); \quad k=0,1,2,…Qk=Φ2k(mod2);k=0,1,2,

We have obtained a formula with which we can fill in the sequence for a billiard table, the width of which is Φ\PhiΦ and the height is 111 . The length of the sequence = ∞\infty , but we can restore part of the pattern by moving from left to right along the sequence and looking into the upper left corner of the billiard table. It remains to figure out how to calculate Φ\PhiΦ

One divided by the golden ratio can be rewritten as:

1Φ=−1+52\frac{1}{\Phi}=\frac {-1+{\sqrt {5}}}{2}Φ1=21+5

We can get rid of the two:

2kΦ=2k(−1+5)2=k5−k\frac{2k}{\Phi}=\frac {2k(-1+{\sqrt {5}})}{2}=k\sqrt{5}-kΦ2k=22k(1+5)=k5k

Our formula takes the form:

Qk=⌊k5−k⌋  (mod  2);k=0,1,2,…Q_k=\lfloor k\sqrt{5}-k \rfloor \; (\textrm{mod} \; 2); \quad k=0,1,2,…Qk=k5k(mod2);k=0,1,2,

Now we can draw part of the billiard pattern with sides 111 and Φ\PhiΦ :

Picture

If we do not subtract kkk each time, then every second bit in the sequence is inverted. We get the general formula:

Qk=⌊kx⌋  (mod  2);k=0,1,2,…Q_k=\lfloor k\sqrt{x} \rfloor \; (\textrm{mod} \; 2); \quad k=0,1,2,…Qk=kx(mod2);k=0,1,2,

Let's build a sequence for k2k\sqrt{2}k2

var x=2;
var q=[];
for(var k=0;k<256000;k++) q[k]=Math.floor(k*Math.sqrt(x))%2;

The first few bits of the sequence (A083035):
01001101100100110011001101100100110110011001001101100100110110…

Angles are 90∘90^{\circ}90 and −90∘-90^{\circ}90 . The size of the initial segment is 5 pixels:

Picture

"This is interesting"

From this curve, we can reconstruct the "billiard pattern" and see what is around the curve:

Picture

It would be interesting to find M and N for this pattern.

Number of segments in the repeating part of the curve = PnP_nPn (Pell numbers: 0, 1, 2, 5, 12, 29, 70, 169, 408, 985, 2378, … ).

Picture

2=lim⁡n→∞Pn−1+PnPn\sqrt{2} = \lim_{n\to\infty} \tfrac{P_{n-1}+P_n}{P_n}2=limnPnPn1+Pn

Someone may doubt that the parity of the integer part of k2k\sqrt{2}k2 gives a fractal sequence. Let's visualize part of this sequence with the visualizer described earlier:

Picture

For clarity, we colored the longest curve in the resulting pattern:

Picture

This curve has a name - "Fibonacci word fractal".

Thus, by gradually reducing billiard geometry through symbolic encodings, we arrive at a powerful realization: even irrational systems, which defy spatial tiling and corner reflection, can still produce deterministic, fractal structure - using only integer math.

Filling the Fractal: From Symbolic Structure to Visual Density

In the previous sections, we showed how symbolic sequences can generate complex boundary structures in discrete 2D space. All of these patterns - whether generated by rational billiards or floor-based symbolic systems - form enclosed regions.
Some of these regions close against the boundaries of the rectangle, while others are fully self-contained, looping within the grid. In either case, the resulting trajectories always define fully enclosed cells.

Consider the following example:

A binary sequence generated by the floor function:

Qn=⌊n2⌋  (mod  2);n=0,1,2,…Q_n=\lfloor n\sqrt{2} \rfloor \; (\textrm{mod} \; 2); \quad n=0,1,2,…Qn=n2(mod2);n=0,1,2,

0100110110010011001001101100

Using the visualizer in diagonal mode, we generate a familiar fractal boundary.

Picture

However, switching to horizontal-vertical visualization, we invert every even-indexed bit and plot dashed lines accordingly. For bits with value 0, the lines are offset by one unit.

Vertical lines:

Picture

Horizontal lines:

Picture

Merged:

Picture

This technique resembles Hitomezashi stitching, a traditional Japanese method of generating textile patterns. While historically used to create decorative designs, this form of boundary generation bears striking similarity to the symbolic outlines produced in our system.

However, Hitomezashi does not solve the filling problem. It provides only the skeleton - the structure of edges - but no mechanism for interior construction.

Picture

A Symbolic Filling Algorithm

To solve this, we developed a symbolic method to automatically fill the interior regions - using only the original sequence. No region detection, no geometry, no search algorithms.

The method works as follows:

Construct a cumulative array a[n], based on the bitwise value of the fractal sequence:

We define:

Qn=⌊nx⌋ mod 2,n=0,1,2,…  Q_n = \lfloor n\sqrt{x} \rfloor \bmod 2, \quad n=0,1,2,\dots \ Qn=nxmod2,n=0,1,2, 

and

an={an−1+1,Qn=1; an−1−1,Qn=0. a_n = \begin{cases} a_{n-1} + 1, & Q_n = 1;\ a_{n-1} - 1, & Q_n = 0. \end{cases} an={an1+1,Qn=1; an11,Qn=0.

In code:

var a = [0];
for (var i = 1; i < size; i++) {
    if (Math.floor(i * Math.sqrt(2)) % 2 == 1)
        a[i] = a[i - 1] + 1;
    else
        a[i] = a[i - 1] - 1;
}

Then, for each cell (x, y), compute:

q = (a[x] + a[y] + 512) % 4;
if (q === 0 || q === 1)
    context.fillRect(x, y, 1, 1);

The result is a filled pattern - not derived from pixel analysis or region marking, but emerging directly from the same symbolic system that generated the boundaries.

Full Algorithm

var a=[0];
for(var i=1;i<size;i++){
    if(Math.floor(i*Math.sqrt(2))%2==1)
        a[i]=a[i-1]+1;
    else
        a[i]=a[i-1]-1;
}
for(var x=0;x<size;x++){
    for(var y=0;y<size;y++){
        q=(a[x]+a[y]+512)%4;
        if(q==0 || q==1) context.fillRect(x, y, 1, 1);
    }
}

Hitomezashi and Symbolic Filling Algorithm

Examples

Fractal fill based on:

Qn=⌊n2⌋  (mod  2);n=0,1,2,…Q_n=\lfloor n\sqrt{2} \rfloor \; (\textrm{mod} \; 2); \quad n=0,1,2,…Qn=n2(mod2);n=0,1,2,

Picture

"Gif"

Picture

Qn=⌊n(5+1)⌋  (mod  2);n=0,1,2,…Q_n=\lfloor n(\sqrt{5}+1) \rfloor \; (\textrm{mod} \; 2); \quad n=0,1,2,…Qn=n(5+1)⌋(mod2);n=0,1,2,

(Fibonacci-based)

Picture

"Gif"

Picture

Interactive

Visualizer - Fractal Fill from Irrationals

fractal.js

Dynamic Visualization - Using Rational Approximations

fractal_dynamic.js

Perfect Shuffle Comparison

Pattern Matching via Perfect Shuffles

We can compare fractal sequences from floor-based systems with sequences produced by a perfect shuffle function.

Here's our shuffle logic:

function shuffle(array, shiftAmount) {
    let len = array.length;
    let shuffled = new Array(len * 2);
    for (let i = 0; i < len; i++) {
        shuffled[2 * i] = array[(i + shiftAmount) % len];
        shuffled[2 * i + 1] = array[i];
    }
    return shuffled;
}

We start with a base array:

let shuffleIterations = 2*7+1;
let powerOfTwo = 2**7;
let shiftAmount = y * powerOfTwo;
let array1 = [1, 0];
for (let i = 0; i < shuffleIterations; i++) {
    array1 = shuffle(array1, shiftAmount);
}

And compare it with this floor-based sequence:

let powerOfTwo = 2**7;
let irrationalApproximation = y / powerOfTwo;
let array2 = [];
for (let i = 0; i < sizexy; i++) {
    array2[i] = Math.floor(i * irrationalApproximation) % 2;
}

Both arrays are then visualized using our bit-pattern analysis:

for (let y = 0; y < sizexy; y++) {
    // generate array1 or array2

    let digit;
    let bits = [];
    for (let i = 0; i < len; i++) {
        digit = 0;
        for (let j = 0; j < bitLength; j++) {
            digit |= array[i + j] << (bitLength - 1 - j);
        }
        if (!bits.includes(digit)) {
            bits.push(digit);
        }
    }
    for (let i = 0; i < bits.length; i++) {
        context.fillRect(bits[i] * size, y * size, size, size);
    }
}

Here are the results:

Perfect shuffle:

Picture

Floor-based sequence:

Picture

Next:

let pow=7;
let shuffleIterations = 2*pow+1;
let powerOfTwo = 2**pow;

let map1=[];
for(let y=0;y<sizexy;y++){
    map1[y]=[];
    let shiftAmount = y * powerOfTwo;
    let array = [0, 1];
    for (let i = 0; i < shuffleIterations; i++) {
        array = shuffle(array, shiftAmount);
    }
    map1[y]=array;
}
drawMap(document.getElementById('myCanvas'), map1);

map2=[];
for(let y=0;y<sizexy;y++){
    let irrational = y / powerOfTwo;
    let array2=[];
    for (let i=0;i<sizexy;i++){
        array2[i]=Math.floor(i * irrational)%2;
    }
    map2[y]=array2;
}
drawMap(document.getElementById('myCanvas1'), map2);

We generate two binary images using two completely different methods.

In the first image, each row is created by starting with [0, 1] and applying a recursive "perfect shuffle" operation. This operation doubles the array size each time and mixes a shifted copy of the previous state with itself. The shift amount depends on the current row number. We repeat this shuffle a specific number of times for each row to reach the final size.

Picture

In the second image, each row is generated by multiplying each column index by a scaled version of the row number, then taking the floor and reducing it modulo 2.

Picture

The two outputs are not just visually similar—they are bitwise identical, pixel by pixel, after horizontal flipping.

We verified this not just through floating-point floor operations, but also with a pure integer formulation using bit shifts:

array2[i] = ((i * y) >> pow) % 2;

This version avoids any irrational approximations entirely. It shows that the mapping:

By(i)=⌊i⋅y2pow⌋ mod 2B_{y}(i) = \left\lfloor \dfrac{i \cdot y}{2^{\text{pow}}} \right\rfloor \bmod 2By(i)=2powiymod2

is equivalent to a symbolic shift-and-fold recursion using perfect shuffles:

  • [0, 1] is shuffled 2·pow + 1 times
  • Each shuffle step doubles the array length
  • Shift is y × 2^pow each time

We also observe that the symbolic structure of the shuffle is time-reversed compared to the floor-based sequence, which explains the horizontal flipping.

This means the perfect shuffle method is not just a metaphor or numerical coincidence — it's an algebraic encoder for binary floor-based mappings.

Theorem (Symbolic Equivalence)

Let:

  • p∈Np \in \mathbb{N}pN
  • N=22p+1N = 2^{2p+1}N=22p+1
  • Shuffley[2p+1]\text{Shuffle}_{y}^{[2p+1]}Shuffley[2p+1] denote the result of applying a recursive perfect shuffle with shift y⋅2py \cdot 2^py2p , starting from [0,1][0, 1][0,1]
  • BinaryFloory(x)=(⌊x⋅y2p⌋ mod 2)\text{BinaryFloor}_{y}(x) = \left( \left\lfloor \dfrac{x \cdot y}{2^p} \right\rfloor \bmod 2 \right)BinaryFloory(x)=(2pxymod2)

Then:

Shuffley[2p+1](x)=1−BinaryFloory(N−x−1)\boxed{\text{Shuffle}{y}^{[2p+1]}(x) = 1 - \text{BinaryFloor}{y}(N - x - 1)}Shuffley[2p+1](x)=1BinaryFloory(Nx1)

This relation holds exactly, using pure bitwise arithmetic.

See:
shuffle_and_billiard_isomorphism.js

Nonlinear Functions and Symbolic Surface Slicing

Symbolic Rotation and the Circle Representation

The binary sequence generated by

⌊k2⌋ mod 2\left\lfloor k \sqrt{2} \right\rfloor \bmod 2k2mod2

can be interpreted geometrically as a rotation on the unit circle. At each step kkk , we rotate by an irrational angle (e.g., 2\sqrt{2}2 ) and assign a 0 or 1 depending on which half of the circle the point lands in.

An alternative but mathematically equivalent formulation is:

sin⁡(πk2)>0\sin\left( \pi k \sqrt{2} \right) > 0sin(πk2)>0

The sine function is positive in one half of the circle and negative in the other - effectively producing the same binary threshold.

Picture

This circular diagram shows the orbit of

k2 mod 1k \sqrt{2} \bmod 1k2mod1

projected onto the unit circle. The points rotate continuously and never repeat. Each crossing of the horizontal axis (i.e., sign change of sin⁡(πk2)\sin\left( \pi k \sqrt{2} \right)sin(πk2) ) causes a binary switch. The result is a Sturmian sequence - a symbolic encoding of irrational rotation - visualized as a point traveling clockwise and recording its hemisphere.

Interestingly, even a sequence like

sin⁡(k)>0\sin\left( k \right) > 0sin(k)>0

generates a similarly complex structure. Though the function seems simple, stepping by exactly 1 radian per iteration is irrational with respect to the sine wave’s natural period of 2π2 \pi2π . Thus:

sin⁡(k)>0⟺⌊kπ⌋ mod 2\sin(k) > 0 \quad \Longleftrightarrow \quad \left\lfloor \frac{k}{\pi} \right\rfloor \bmod 2sin(k)>0πkmod2

Which means: irrational step size alone is enough to create symbolic fractals. It’s not the shape of the function - it’s the incommensurability that matters.

Geometric Interpretation of Linear Discretization

We begin with a geometric interpretation of the function

⌊k2⌋ mod 2\left\lfloor k \sqrt{2} \right\rfloor \bmod 2k2mod2

This can be visualized as a straight line y=k2y=k \sqrt{2}y=k2 traversing a periodic 2D space where the yyy -axis alternates between bands labeled 0 and 1. The value of the function at each step depends on the integer part of k2k\sqrt{2}k2 , determining whether the line intersects an even or odd band.

Picture

Alternatively, we may interpret the system as a function y=xy=xy=x with 2\sqrt{2}2 acting as a discretization step along the vertical axis. This perspective reduces the behavior of the original billiard system to a symbolic sampling of a continuous linear function.

Both

⌊k2⌋ mod 2andsin⁡(πk2)>0\left\lfloor k \sqrt{2} \right\rfloor \bmod 2 \quad \text{and} \quad \sin\left( \pi k \sqrt{2} \right) > 0k2mod2andsin(πk2)>0

serve as symbolic discretization methods - one yielding binary values via integer floor division, the other through sign thresholding on a continuous sinusoid.

Transition to Quadratic Functions

Having reduced the system to a linear function and its discretization, we now explore the effects of replacing the base function y=xy=xy=x with a nonlinear alternative.

Linear rotation yields symbolic Sturmian sequences. What happens if we increase the curvature? Quadratic growth is the simplest next step.

We now substitute the linear function with:

y=x2y = x^2y=x2

We construct the new sequence using:

Qx=⌊x22⌋  (mod  2);x=0,1,2,…Q_x=\lfloor x^2\sqrt{2} \rfloor \; (\textrm{mod} \; 2); \quad x=0,1,2,…Qx=x22(mod2);x=0,1,2,

q[x] = Math.floor(x * x * Math.sqrt(2)) % 2;

This substitution shifts us from uniform linear growth to a system governed by accelerating curvature, producing richer and more complex symbolic behavior.

Visualizing this sequence with the Symbolic Filling Algorithm yields a disordered pattern.

Picture

"Gif"

Picture

Similarly, applying Turtle graphics results in "chaotic" outputs

Picture

suggesting that the underlying symbolic dynamics differ significantly from the linear case. This observation motivated us to try a simpler visual encoding.

This prompts a reconsideration of visualization methods. Rather than relying on complex binary sequence encodings (e.g., symbolic filling or turtle graphics), we adopt a simpler approach:

  1. Place the first k elements of the sequence q[x] in the initial row.
  2. For each subsequent row along the y-axis, use q[x+ky].
  3. The result is a striking array of structured, interference-like patterns.

k=35:

Picture

k=661:

Picture

This reveals that a seemingly chaotic 1D sequence can exhibit coherent spatial behavior when unfolded along two dimensions. Generalizing this, we rewrite the indexing expression as:

q[x] = Math.floor((x + k * y) ** 2 * Math.sqrt(2)) % 2;

Expanding the square:

(x+ky)2=x2+2kxy+k2y2(x + k y)^2 = x^2 + 2kxy + k^2 y^2(x+ky)2=x2+2kxy+k2y2

This quadratic form suggests a symbolic sampling of a 3D curved surface. We abstract this into a general expression:

z=a(x2+bxy+cy2)dz = a \left( x^2 + bxy + c y^2 \right)^dz=a(x2+bxy+cy2)d

Here:

  • aaa controls vertical scaling (the discretization frequency),
  • bbb introduces diagonal shear,
  • ccc modulates stretching along the yyy -axis,
  • and ddd introduces curvature nonlinearity.

For example, setting b=0,c=1,d=1b=0,c=1,d=1b=0,c=1,d=1 yields:

z=a(x2+y2)z = a \left( x^2 + y^2 \right)z=a(x2+y2)

an elliptical paraboloid, a classic bowl-shaped surface.

Picture

We then visualize both:

⌊z2⌋ mod 2\left\lfloor z \sqrt{2} \right\rfloor \bmod 2z2mod2

sin⁡(πz2)\sin\left( \pi z \sqrt{2} \right)sin(πz2)

...using this surface. Despite differing in output (binary vs. continuous), both render structurally equivalent patterns: the sine version produces smooth grayscale textures, while the floor function yields crisp binary segmentation. In either case, the resulting 2D images exhibit radial, interference-like motifs - strongly reminiscent of diffraction or holographic patterns.

binary continuous

The sine-based rendering reveals finer gradients and smoother interference zones, but the underlying symbolic structure is identical to the binary version.

Holographic Analogy

In classical holography, a point source emits nested spherical wavefronts. When these are sliced by a flat recording plane, the amplitude at each (x, y) position encodes a continuous interference pattern. The spacing between wavefronts defines the wavelength - effectively a discretization step in the z-direction.

Our system inverts this paradigm: instead of slicing nested curved shells with a flat surface, we intersect a single curved surface with stacked, evenly spaced binary planes - symbolic layers representing a plane wavefront. Each (x, y) coordinate samples which symbolic layer the surface intersects, producing a binary (or thresholded) value.

While the components differ - continuous vs symbolic, curved emitter vs curved surface - the underlying mechanism is the same: a curved geometry intersected by layered structure, producing interference-like textures from simple spatial rules.

Despite differences in physical interpretation, both systems share a core structure: curved geometry meets layered slicing - and complexity emerges.

Our picture size is 400 pixels. We used a=1400a=\frac{1}{400}a=4001 for previous picture to fit the picture.

Here another pattern with a=1200a=\frac{1}{200}a=2001 :

binary continuous

ccc modulates stretching along the yyy -axis

(we will use continuous patterns from now).

c=2c=2c=2 c=0.2c=0.2c=0.2

bbb introduces diagonal shear

b=−1.5b=-1.5b=1.5 b=1.5b=1.5b=1.5

For b=0,c=−1,d=1b=0,c=-1,d=1b=0,c=1,d=1 our equation becomes:

z=a(x2−y2)z=a(x^2-y^2)z=a(x2y2)

This is a hyperbolic paraboloid - a surface with negative Gaussian curvature:

Picture

a=1400a=\frac{1}{400}a=4001 a=1200a=\frac{1}{200}a=2001

For b=0,c=1,d=1/5b=0, c=1, d=1/5b=0,c=1,d=1/5 our equation becomes:

z=a(x2+y2)1/5z=a(x^2+y^2)^{1/5}z=a(x2+y2)1/5

Picture

a=1a=1a=1 a=10a=10a=10
a=100a=100a=100 a=1000a=1000a=1000

The most interesting patterns are obtained if we take a ddd that differs slightly from 1. For example, for

b=0,c=1,d=11.01b=0, c=1, d=\frac{1}{1.01}b=0,c=1,d=1.011

a=18258a=\frac{182}{58}a=58182 a=173165a=\frac{173}{165}a=165173
a=170109a=\frac{170}{109}a=109170 a=11170a=\frac{111}{70}a=70111
a=57178a=\frac{57}{178}a=17857 a=186119a=\frac{186}{119}a=119186

b=1,c=1,d=11.01b=1, c=1, d=\frac{1}{1.01}b=1,c=1,d=1.011

a=174111a=\frac{174}{111}a=111174 a=50152a=\frac{50}{152}a=15250

Interactive

Static Visualization

hologram_s.js

Dynamic Visualization

hologram_dynamic.js

Hologram Experiment

hologram_reconstruction.html

Conclusion

This study began with a simple system: a billiard ball reflecting within a rectangular grid. By examining its trajectory and translating spatial behavior into symbolic sequences, we uncovered patterns exhibiting recursive structure, boundary self-similarity, and interference-like properties.

Through progressive abstraction - from 2D reflections to 1D symbolic sequences, and eventually to nonlinear surfaces - we showed that binary patterns can emerge from discretized irrational steps alone. Formulas such as:

Qk=⌊kx⌋ mod 2andQk=sin⁡(πkx)>0Q_k=\left\lfloor k \sqrt{x} \right\rfloor \bmod 2 \quad \text{and} \quad Q_k=\sin\left( \pi k \sqrt{x} \right) > 0Qk=kxmod2andQk=sin(πkx)>0

generate deterministic sequences that yield quasi-fractal geometries when visualized spatially. Though entirely discrete, these systems exhibit behaviors commonly associated with continuous wave phenomena.

Further generalization using surface equations of the form:

z=a(x2+bxy+cy2)dz = a \left( x^2 + bxy + c y^2 \right)^dz=a(x2+bxy+cy2)d

reveals that curvature, shear, and nonlinearity shape the resulting symbolic slices in ways reminiscent of optical interference. The resemblance between these binary patterns and holographic textures suggests a structural parallel, despite their different origins.

No physical claims are made. However, the symbolic systems presented here demonstrate that simple integer-based operations, applied to irrational quantities or curved domains, can generate high-order structure with properties of both visual and mathematical interest. This offers a conceptual bridge between number theory, symbolic dynamics, and emergent spatial organization.

While this study has uncovered significant insights, several open questions remain to inspire further research:

  1. Generalization to Non-Fibonacci Ratios. The recursive generators presented here excel for Fibonacci-based rectangles, but can similar symbolic encoding schemes be developed for arbitrary co-prime pairs or other number sequences (e.g., Lucas numbers, Pell numbers)? What universal properties govern the resulting fractal structures?
  2. Irrational Billiards and Sequence Ordering. For billiard tables with incommensurable sides (e.g., 1 : φ), we partially addressed pattern generation using floor-based sequences. However, can a robust method be devised to order these sequences consistently, enabling full reconstruction of the pattern in the absence of grid alignment?
  3. Perfect Shuffle and Floor-Based Equivalence. The striking similarity between perfect shuffle sequences and irrational floor-based sequences suggests a potential mathematical identity. Is there a formal equivalence between these systems, or do they converge only under specific conditions? What deeper structures might unify these approaches?
  4. Nonlinear Surface Generalizations. The transition to quadratic and higher-order surfaces produced rich, holographic-like patterns. How do variations in the exponent (d) or coefficients (a), (b), and (c) affect the fractal dimension or complexity of the resulting patterns? Can these be analytically quantified?
  5. Applications to Physical Systems. The visual resemblance to holographic interference patterns raises the question: can these symbolic systems model real-world wave phenomena, such as optical diffraction or quantum interference, in a computationally efficient way? These questions highlight the potential for further exploration at the intersection of symbolic dynamics, fractal geometry, and computational visualization. By bridging discrete mathematics with continuous phenomena, this work offers a foundation for investigating how simple rules can encode complex, emergent behaviors - potentially extending to fields like number theory, physics, and computer graphics.

GitHub repository: https://github.com/xcontcom/billiard-fractals

// Detect dark theme var iframe = document.getElementById('tweet-1941606569273155829-901'); if (document.body.className.includes('dark-theme')) { iframe.src = "https://platform.twitter.com/embed/Tweet.html?id=1941606569273155829&theme=dark" }

AI Dominates Global Tech Landscape: From Chipsets and Scientific Ambitions to Job Market Shifts and Financial Markets.

2025-11-28 11:02:45

The Artificial Intelligence landscape is in rapid flux, touching everything from hardware innovation to the very definition of intelligence and its impact on the global economy and workforce. This post serves as a technical primer on recent developments:

  • Hardware Advancements: Qualcomm's Snapdragon 8 Gen 5 platform is pushing the boundaries of mobile processing power and AI capabilities, crucial for edge AI applications.
  • Cognitive AI Research: A significant study in Nature Human Behaviour questions the fundamental assumptions linking language models to human-level reasoning, suggesting that AI's path to true cognition might be more complex than previously thought. This has implications for research in natural language processing (NLP) and artificial general intelligence (AGI).
  • Interdisciplinary AI Integration: The increasing demand for neuroscientists in AI companies highlights a growing trend of cross-disciplinary research, aiming to leverage insights from neuroscience to build more sophisticated AI architectures. This could influence algorithm design and computational neuroscience.
  • National AI Strategies: The US 'Genesis Mission' is a large-scale initiative leveraging supercomputing and national labs to accelerate AI research, akin to the historical 'Manhattan Project.' Similarly, China's establishment of an 'Industrial Artificial Intelligence Institute' signals a strategic push towards AI integration in manufacturing, focusing on intelligent systems and high-quality production.
  • Economic and Labor Market Impacts: Layoffs at companies like HP and Uber, partly attributed to AI implementation and project recalibrations, underscore the immediate economic consequences of AI adoption. This necessitates a discussion on workforce adaptation, reskilling, and the ethical considerations of automation.
  • Generative AI Tools: Alibaba's open-source release of Z-Image signifies continued innovation in generative models, providing developers with new tools for image creation and manipulation. This area is ripe for exploration in computer vision and machine learning frameworks.
  • Digital Sovereignty and Geopolitics: Canada's focus on digital sovereignty amidst the global AI race points to the increasing geopolitical significance of AI development, data control, and technological infrastructure.
  • Financial Market Implications: Tether's substantial gold accumulation raises questions about the evolving role of stablecoins and their backing mechanisms within the broader financial ecosystem.
  • Investment and Market Analysis: Despite concerns about potential AI bubbles, market analysts project significant growth, indicating strong investor confidence and continued R&D investment in AI technologies.