# Create a triangle whose colors are determined by the bitsums of coordinates

Write a program that, for any $$\n\$$, generates a triangle made of hexagons as shown, $$\2^n\$$ to a side. The colors are to be determined as follows.

We may give the triangle barycentric coordinates so that every hexagon is described by a triple $$\(x,y,z)\$$ with $$\x+y+z=2^n-1\$$. (The three corners will be $$\(2^n-1,0,0)\$$, $$\(0,2^n-1,0)\$$, and $$\(0,0,2^n-1)\$$.)

Let $$\s_2(n)\$$ refer to the number of 1s in the binary expansion of $$\n\$$. (This is sometimes called the bitsum or the popcount function.) If $$s_2(x)+s_2(y)+s_3(z)\equiv n\pmod 2$$ then color the hexagon $$\(x,y,z)\$$ in a light color; otherwise, color it in a dark color. (These must be colors, not simply black and white.)

In your answer, I would appreciate seeing several example outputs, ideally including $$\n=10\$$.

This is my first post here, so I apologize if I misunderstand the rules somehow.

This is a code golf challenge, so shortest code (in bytes) wins.

• Why is the LaTeX not working? EDIT: Thank you! @RydwolfPrograms Commented Feb 13, 2023 at 22:57
• CGCC uses a backslash before the $, so it'll be $n$ Commented Feb 13, 2023 at 22:58 • For what it's worth, I do not know if this fractal has a name or if it has been studied before. If $A_n$ denotes the number of light cells connected to the edges, I believe they satisfy the recurrence relation $A_{n+3}=3A_{n+2}+9A_{n+1}-24A_n$. Commented Feb 13, 2023 at 23:02 • Welcome to Code Golf and nice first question! Challenges on this side need to have an objective scoring criteria. Is this a code golf challenge? If so, please add the code-golf tag. Commented Feb 14, 2023 at 1:43 • @alephalpha I mean, personally all I care about is that people make something that works, but in the interest of making an objective score I might as well make it code golf. Commented Feb 14, 2023 at 2:01 ## 4 Answers # Wolfram Language (Mathematica), 119 bytes -1 byte thanks to @att. Graphics@Table[{Hue[Tr[ThueMorse@{x,y,s-x-y}+#+1]/2],RegularPolygon[{2x+y,√3y},{1,Pi/2},6]},{x,0,s=2^#-1},{y,0,s-x}]&  • Ooh! This also gets closest to a regular aspect ratio out of the ones so far, I think. [EDIT: The aspect ratio of the JavaScript one depends on if I view it on my phone or laptop, it seems.] Who knew that Mathematica has a "Thue Morse" function ready to go? Commented Feb 14, 2023 at 2:34 • (Tr@ThueMorse@...+#+1)/2->Tr[ThueMorse@...+#+1]/2 – att Commented Feb 14, 2023 at 7:47 • @AkivaWeinberger For my answer I just picked a value for line-height that I thought looked good by eye; feel free to alter it to get a better aspect ratio. – Neil Commented Feb 14, 2023 at 8:34 • @AkivaWeinberger Well, you might expect _Math_ematica to have built-in mathematical functions. At least, more so than animal recognition. Commented Feb 16, 2023 at 19:17 ## JavaScript (ES76), 191187180174172168 152 bytes f= n=>eval('s="<center style=line-height:.7>";for(i=-1;++i<1<<n;s+="<br>")for(j=i+1;j--;)s+=<font color=#f${(g=n=>n?9-g(n&n-1):9)(i^j^i-j)}0>⬢</font>')
<input type=number min=0 max=10 onchange=o.innerHTML=f(+this.value)><div id=o style=font-size:5px>

Output format is HTML. Snippet limited to n=10 because it triggers my browser's slow script warning if you go any higher. (But the output is too big for my screen anyway.) Edit: Saved 4* 11 bytes by simplifying the parity calculation. Saved 6 8 23 bytes thanks to @Ausername. Saved 4* 5 bytes thanks to @EzioMercer.

*crossed out 4 is still regular 4

• Very nice! How does it check the bit parities? Commented Feb 14, 2023 at 1:12
• @AkivaWeinberger n^i, j and i-j are the barycentric coordinates, but to compare their parity with n, I ^ (XOR) everything together, and the n^n cancels out, leaving i^j^i-j. The result is converted to binary and pairs of 1s are deleted. If any 1s are left then you get red otherwise you get tan.
– Neil
Commented Feb 14, 2023 at 1:28
• Depending on how far you're prepared to go, you could either add a color=# and use 3-digit hex codes b) use 2 or even 1-digit hex codes. Also, the font tag doesn't need to be closed. Commented Feb 14, 2023 at 2:28
• You might also be able to ave some bytes by reversing the loops and using j-- and similar as the condition, although that might need some rearanging Commented Feb 14, 2023 at 2:30
• @emanresuA I don't really want to contemplate 522753 nested unclosed font tags. Also, I'm not sure that #990 is light enough to qualify as light. I originally did try having the loops descending but I didn't want to invert the triangle. On the other hand I have just seen an obvious 7 byte save after my previous edit.
– Neil
Commented Feb 14, 2023 at 8:32

# C++ using SFML : 722703683527411 399 bytes

-19 bytes thanks to NoLongerBreathedIn, using __builtin_popcount removes needing a bitsum function. Might work only for GCC.

-20 bytes, I used the using keyword for namespaces and components, and stopped using .f for magic numbers

-156 bytes thanks to pan

-116 bytes again thanks to pan

-12 bytes thanks to ceilingcat and pan

pan's proposed version approximates the value of cos(210) to around -.86, which will produce a slightly different graphic output, but very close to what's required by the challenge. This makes the cmath include useless. He also put the whole code into one function, and used a number of golfy techniques to reduce more the byte count, which makes the result very nice. His second optimization renders the use of vector useless, making an include and object usage useless

pan's code :

#include<SFML/Graphics.hpp>
#define B+__builtin_popcount(
void v(int n){sf::CircleShape h(4,6);for(sf::RenderWindow w({1200,1000},"");w.isOpen();w.display()){for(sf::Event e;w.pollEvent(e);)e.type?h.setOrigin(-600,-650):w.close();w.clear();for(int x=0,y,z=1<<n;x<z;)for(y=x++-z;y++;)h.setPosition(4.3*(2*y+z-x),2.5*(2+z-3*x)),h.setFillColor(sf::Color(B-x)B-y)B z+y-x)-n&1?65535:-65281)),w.draw(h);}}


SFML is a library that helps with the development of graphical / audio / network applications.

Previous 683 bytes answer (with the "exact" value or cos(210°)) :

#include <cmath>
#include <vector>
#include <SFML/Graphics.hpp>
#define B(c) __builtin_popcount(c)
using namespace sf;struct t{double x,y;bool b;};using V=std::vector<t>;V d(int n){double r=5;int x,y,z,w=pow(2,n);V o;for(x=0;x<w;++x)for(y=0;y<w-x;++y){z=w-1-x-y;o.push_back({-cos(7*M_PI/6)*(r*y-r*z),r*x-(r*y+r*z)/2,(B(x)+B(y)+B(z))%2==n%2});}return o;}int v(int n){RenderWindow w(VideoMode(1200,1000),"");CircleShape h(4,6);;auto v=d(n);while(w.isOpen()){Event event;while(w.pollEvent(event))if(event.type==Event::Closed)w.close();w.clear();for(auto&a:v){h.setPosition(a.x,-a.y);h.setOrigin(-600,-650);h.setFillColor(a.b?Color::Yellow:Color::Blue);w.draw(h);}w.display();}return 0;}


Function to call in the main is v(int) with the parameter being n, the number n

int main() {
return v(6);
}


Compile with : g++ source.cpp -lsfml-graphics -lsfml-window -lsfml-system

Run with : ./a.out

Due to the screen size and the fact that hexagons have to be visible, the size of a n=10 triangle can't be seen fully in a 'normal' sized screen, triangle is fully visible in the screen at n<=7. Size of hexagon and space between them can be configured in the d(int) function with variable r and v(int) function by modifying the first parameter of the constructor of the h variable (the CircleShape object), that value being the radius of the circle. Be free to modify those parameters to draw bigger hexagons on the screens, r should be slightly bigger that the circle's radius

Here is an image of the result for n=6

• Would using __builtin_popcount shorten the code? Commented Feb 15, 2023 at 1:55
• 527
– pan
Commented Feb 19, 2023 at 9:01
• 411
– pan
Commented Feb 19, 2023 at 21:44
• 399 building on @ceilingcat
– pan
Commented Feb 20, 2023 at 1:47

# Wolfram Language (Mathematica), 222 bytes

n=6;c=Graphics[{#,Rotate[Polygon@CirclePoints@6,30Degree]},ImageSize->9]&;Column[Row/@TakeList[(Tr@DigitCount[#,2,1]~Mod~2&/@Reverse@Select[Range[0,h=2^n-1]~Tuples~3,Tr@#==h&])/.{1->c@Red,0->c@Blue},Range[2^n]],Center,.01]