Some people will claim that I am cheating with this one; and they are probably right... but it was fun to develop and it kind of works (although only with odd numbers 😭). The idea is:
Create a SVG image that shows an asterisk with text.
Put that SVG as an inline background image for an element.
Clip the element to only show a diamond shape (using clip-path).
Define a CSS variable to specify the number of stars in the middle of the diamond.
Knowing the size of the SVG image, use the CSS variable to calculate the height and width of the element.
funcdiamond(centerint)(string,error){if(center&1)==0{return"",errors.New("center row must be an odd number")}returnstrings.Join(makeDiamond(center),"\n"),nil}funcdiamondOfDiamonds(centerint)(string,error){if(center&1)==0{return"",errors.New("center row must be an odd number")}dmd:=makeDiamond(center)outBuf:=make([]string,center)row:=strings.Repeat(" ",center)fori:=0;i<=center/2;i++{rowBuf:=make([]string,center)forj:=rangerowBuf{rowBuf[j]=strings.Repeat(row,center/2-i)+strings.Repeat(dmd[j],2*i+1)+strings.Repeat(row,center/2-i)}outBuf[i],outBuf[center-i-1]=strings.Join(rowBuf,"\n"),strings.Join(rowBuf,"\n")}returnstrings.Join(outBuf,"\n"),nil}funcmakeDiamond(centerint)[]string{outBuf:=make([]string,center)row:=bytes.Repeat([]byte{' '},center)forl,r:=(center/2),(center/2);l>=0;l,r=l-1,r+1{row[l],row[r]='*','*'outBuf[center/2-l],outBuf[center/2+l]=string(row),string(row)}returnoutBuf}
Full-stack dev shipping Django/React SaaS and Shopify stores since 2018. 37 client projects, 11 live Shopify builds. I write production war stories so you don’t repeat my outages.
Full-stack dev shipping Django/React SaaS and Shopify stores since 2018. 37 client projects, 11 live Shopify builds. I write production war stories so you don’t repeat my outages.
Gave it a try in Python. Not exactly as required since the diamond is printed on-the-fly, but I think it shows the main idea to create every line one after the other. Could also be stored in a string and then returned...
functiondrawDiamond($diameter){if($diameter<=2){trigger_error("provide more than 2 in diameter at least ! ",E_USER_WARNING);}else{$code="<pre style='text-align: center; font-size: 22px;'>";for($i=1;$i<$diameter;$i+=2){$code.=str_repeat("*",$i)."<br>";}for($i=$diameter;$i>=1;$i-=2){$code.=str_repeat("*",$i)."<br>";}$code.="</pre>";return$code;}}echodrawDiamond(11);
I would like to add:
1) Making str.center do some of the dirty work
2) Using ranges (and chain) to iterate up and down instead of keeping a state on num
fromitertoolsimportchaindefdiamond(n):ifn<=0orn%2==0:raiseValueError('n must be odd and positive')foriinchain(range(1,n+1,2),reversed(range(1,n,2))):print(('*'*i).center(n))diamond(1)diamond(3)diamond(5)
It might be more readable to have two loops instead of using chain but I like chaining more because I don't need to repeat the print
Full-stack dev shipping Django/React SaaS and Shopify stores since 2018. 37 client projects, 11 live Shopify builds. I write production war stories so you don’t repeat my outages.
I wouldn't worry about it too much, since print requires IO, it is by far the bottleneck.
For the rest of the utilities that I used: range, chain, and str.center: they are all implemented in C if you are using the standard CPython (should be fast).
To avoid the IO, let's compare the two functions as generators of strings (I replaced the print with yield (('*' * i).center(n)) for both my implementation and Nicks:
In [39]: %timeit tuple(my_diamond(11))
3.59 µs ± 37.6 ns per loop (mean ± std. dev. of 7 runs, 100000 loops each)
In [40]: %timeit tuple(nicks_diamond(11))
4.66 µs ± 69.9 ns per loop (mean ± std. dev. of 7 runs, 100000 loops each)
Seems like mine is slower than Nicks.
However, on my machine, a single print statement takes about 4.17us, which is almost as long as diamond(11) takes without any prints!
Full stack web dev.
Studying FP web development approaches, while helping Mission Bit create paths to programming for underserved public school kids.
Previously @ Gradescope.
Here my solution: form the upper side and reuse it.
Assuming string concatenation has linear execution time, this solution should be O(middle*num). Please correct me if I'm wrong
functiondiamond(num){if(num%2<=0)returnnull;letresult="";constmiddle=Math.floor(num/2)+1;letlines=[]for(leti=0;i<middle;i++){lines[i]="";for(letj=0;j<num;j++){lines[i]+=j>=middle-1-i&&j<=middle-1+i?"*":"";}result+=lines[i]+"\n";}// reuse the trianglefor(leti=lines.length-2;i>=0;i--){result+=lines[i]+"\n";}returnresult;}
This took me longer than it should have. But I haven't worked with R in almost 2 years. Sure you could do it more efficiently with just a loop, but I learned some stuff about concatenating matrices to strings in R this way so I call it a win.
C# Just two main loops to print upper and lower part. One loop to calculate no of rows
var diagonalLength = int.Parse(Console.ReadLine());
if (diagonalLength %2 == 0 || diagonalLength < 0)
{
Console.WriteLine("null");
Console.ReadKey();
return;
}
var rowCount = 0;
// calculate the no of rows needed
for (int i = 1; i < diagonalLength; i += 2)
{
rowCount += 1;
}
var number = diagonalLength;
var j = rowCount;
// upper part of the diamond
for (int i = 1; i <= number; i += 2, j--)
{
Console.Write(new string(' ', j));
Console.Write(new string('*', i));
Console.WriteLine(new string(' ', j));
}
j = 1;
number = diagonalLength - 2;
// lower diamond
for (int i = number; i >= 1; i -= 2, j++)
{
Console.Write(new string(' ', j));
Console.Write(new string('*', i));
Console.WriteLine(new string(' ', j));
}
// Will print a diamond with n stars in the middle linefunctionprintDiamond(n){// validate inputif(n%2===0)thrownewError("can't have middle row size of an even number");if(n<0)thrownewError('input must be a positive number');constnumLines=n;letspaces=n-1;letstars=1;constmiddleLine=Math.floor(numLines/2);for(leti=0;i<numLines;i++){console.log(buildLine(stars,spaces));// before the middle line we will increment the number of stars by 2if(i<middleLine){stars+=2;spaces-=2;}// after the middle line we decrement the number of stars by 2else{stars-=2;spaces+=2;}}}// will build a line with the correct number of stars and spaces// ie given 3 stars and 2 spaces// will build ' *** 'functionbuildLine(stars,spaces){letline='';constlineSize=stars+spaces;// the first index in the line with a star.conststarIndex=Math.floor((lineSize-stars)/2);for(leti=0;i<lineSize;i++){// starts building starsif(i>=starIndex&&stars>0){line+='*';stars--;}elseline+='';}returnline;}
deviated from the spec in one specific way where I don't return null if a an even number or negative number is provided but instead throw an error.
I feel however this gives more information to the user.
publicstaticstringDiamond(ulongn){if((n%2)==0)returnnull;ulongmaxIndent=(n-1)/2;StringBuildersb=newStringBuilder();sb.WriteRows(maxIndent,maxIndent,end=>end>0,i=>i-1);sb.WriteRows(maxIndent,0,end=>end<=maxIndent,i=>i+1);returnsb.ToString();}publicstaticvoidWriteRows(thisStringBuildersb,ulongmaxIndent,ulongstart,Func<ulong,bool>condition,Func<ulong,ulong>step){for(ulongindent=start;condition(indent);indent=step(indent)){sb.WriteChars(indent,' ');sb.WriteChars(maxIndent-indent,'*');sb.Append("*");sb.WriteChars(maxIndent-indent,'*');sb.WriteChars(indent,' ');sb.WriteLine();//make a NewLine}}privatestaticvoidWriteChars(thisStringBuildersb,ulongcount,charc){for(ulongi=0;i<count;++i){sb.Append(c);}}
import'dart:io';main(){stdout.writeln('Center Lenght?');intcenter=int.tryParse(stdin.readLineSync());if(center==null||center%2==0){print('Center can\'t be null or an even number');}for(vari=1;i<center;i+=2){print((" "*((center-i)~/2))+("*"*i));}for(vari=center;i>=1;i-=2){print((" "*((center-i)~/2))+("*"*i));}}
Second year Computer Science student with an interest in web/mobile development, big data, robotics and cyber security. Probably drinking too much coffee or coding to avoid doing other coding...
constdrawRow=(qty,replaceWith)=>{letstr="";for(leti=0;i<qty;i++){str+=replaceWith;}returnstr;};constprintDiamond=(n)=>{if(n%2===0||n<0){return"The number should be odd and positive";}letrow="";letstars=0;for(leti=0;i<n;i++){if(i>parseInt(n/2)){stars-=2;}else{stars=i*2+1;}constspaces=(n-stars)/2;row+=drawRow(spaces,"");row+=drawRow(stars,"*");row+=drawRow(spaces,"");if(i!==n-1){row+="\n";}}returnrow;};console.log(printDiamond(11));
defdiamond(n):# Make some diamonds!
ifn%2==0orn<=0:returnNoneifn==1:return"*\n"array=list(range(1,n+1))result=""white_space_count=list(range(1,int((n-(n%2))/2)+1))white_space_count.reverse()white_space_index=0forcountinarray:ifcount%2==0:continueifwhite_space_index!=len(white_space_count):result+=(" "*white_space_count[white_space_index])white_space_index+=1result+=("*"*count)+"\n"array.reverse()array=array[1:]white_space_count.reverse()white_space_index=0forcountinarray:ifcount%2==0:continueifwhite_space_index!=len(white_space_count):result+=(" "*white_space_count[white_space_index])white_space_index+=1result+=("*"*count)+"\n"returnresult
print((lambdamaxStars=int(input("Star Count: ")):"Can't be a star =("ifnotmaxStars%2else"".join(map(lambdai:"".join([" "]*(int((maxStars-((i+1)*2-1if(i+1)*2-1<=maxStarselse(maxStars-(i+1)+1)*2-1))/2))+["*"]*((i+1)*2-1if(i+1)*2-1<=maxStarselse(maxStars-(i+1)+1)*2-1))+"\n",range(maxStars))))())
No one will see this but I spent a couple of hours trying to figure it out:
#include <iostream>
// value dictates total number of asterisks in middle rowboolprint(intvalue){// if user value is even, or equal to zeroif((value%2)==0||value==0){returnfalse;}// iterate through each possible ascending rowfor(inti{0};i<=value;++i){// only print new row on odd-numbered valuesif((i%2)!=0){// print buffer for alignmentfor(intj{0};j<((value-i)/2);++j){std::cout<<" ";}// print this rowfor(intk{0};k<i;++k){std::cout<<"*";}std::cout<<'\n';}}// iterate through each possible descending row// avoid printing the middle row twicefor(inti{value-1};i>0;--i){// only print new row on odd-numbered valuesif((i%2)!=0){// print buffer for alignmentfor(intj{0};j<((value-i)/2);++j){std::cout<<" ";}// print this rowfor(intk{0};k<i;++k){std::cout<<"*";}std::cout<<'\n';}}returntrue;}intmain(){if(!print(11)){std::cout<<"invalid input detected!"<<'\n';}}
Very late to the party here, but wanted to post another python solution.
Takes advantage of using string formatting to center the text, simplifying the code, also using chain from itertools to stack to range functions together.
Implemented this in rust with some tests. I am still learning and got a lot of experimentation done. Idk how much it matters in this case but I tried pre-allocating capacities for any vectors or strings.
At first I used modulo to get uneven numbers in the for loop but I got stuck doing it.
Fond a solutuion here in the comments of a guy using abs-values, that inspired me to instead only create the diamond up to its mid-row and then reflect it around that row.
Could maybe improve and use iterators instead of for-loop, idk?
with.capacity(), seems to take usize only, some improvement could be done here, for example I convert to usize for each capacity call.
Adding the padding at the end of a line isnt really neccessary?
fndiamond(length:i32)->Option<String>{// Return early with None if len less than 1iflength<1{returnNone;}// Find mid-row/mid-point // and pre-alloc capacity for output-vector// note capacity seems to determine amnt of elements// not capacity to hold data(?)letmidpoint=(length+1)/2;letmutoutput=Vec::with_capacity(lengthasusize);// Create each line up to and including midrow, padding decreases// => asterixes increasesforiin1..=midpoint{letmutline=String::with_capacity(lengthasusize);letpad=midpoint-i;letpadding=concat_char_cap(' ',pad);letasterix=concat_char_cap('*',length-pad*2);// push the strings together to form the lineline.push_str(&padding);line.push_str(&asterix);line.push_str(&padding);line.push_str("\n");// push into output_vectoroutput.push(line);}//reflect half of the vector around its center row// maybe this could save some computation for// larger diamondsletmutbeg=output[0..output.len()-1].to_vec();beg.reverse();output.append(&mutbeg);// create iterator and collect into String.// wrap around SomeSome(output.into_iter().collect())}fnconcat_char_cap(c:char,n:i32)->String{// pre-alloc string with capacity, // maybe its more efficient for larger rowsletn=nasusize;letmutoutput=String::with_capacity(n);ifn==1{output.push(c);}elseifn>1{for_iin0..=n-1{output.push(c);}}output}fnmain(){println!("{:?}",diamond(0));}#[cfg(test)]modtests{usesuper::*;#[test]fncase_successful_dimaond(){letmidrow=5;letexpected=" \
*
***
*****
***
* \n".to_string();assert_eq!(diamond(midrow),Some(expected));}#[test]fncase_empty_diamond(){letmidrow=0;assert_eq!(diamond(midrow),None);}#[test]fncase_negative_diamond(){assert_eq!(diamond(-2),None)}}
func BuildAsteriskDiamond(weight int) (string, error) {
if weight < 3 {
return "", errors.New("Can't build diamond less than 3 asterisk")
}
if weight % 2 == 0 {
return "", errors.New("Even number is not allowed!")
}
result := ""
var height int = weight / 2
var lineWidth int = height + 1
asteriskCount := 1
for i := 0; i < weight; i++ {
spacesCount := abs(height - i)
result = result + repeatCharacter(" ", spacesCount) + repeatCharacter("*", asteriskCount) + "\n"
if i < height {
asteriskCount += 2
lineWidth++
} else {
asteriskCount -= 2
lineWidth--
}
}
return result, nil
}
func repeatCharacter(character string, count int) string {
result := ""
for i := 0; i < count; i++ {
result += character
}
return result
}
func abs(x int) int {
if x < 0 {
return -x
}
return x
}
I didn't find any good solution to abs integer in go :(
I am an OpenEdge (aka Progress) developer that loves clean code and good looking applications that are easy to use. My main pet project is the Progress DataDigger
Coding since 11yo, that makes it over 30 years now ~~~
Have a PhD in Comp Sci ~~~
Love to go on bike tours ~~~
I try to stay as generalist as I can in this crazy wide place coding is at now.
CSS
Some people will claim that I am cheating with this one; and they are probably right... but it was fun to develop and it kind of works (although only with odd numbers 😭). The idea is:
Here there is a working demo on Codepen:
Wow amazing one again! I don't think it's cheating at all, just a creative solution to the problem!
Thanks!
Yesterday's solution was definitely more cheating than this one.
Good job! :)
Amazing! You are a CSS master!
After @andrewbrown shamed us all yesterday for not having test cases, I decided I needed to step up my game and went full TDD with this one!
Rust Solution:
+1 for Rust
+1 for TDD
Nice!
Hey! Also JavaScript
This is my favorite JS answer to this challenge 👍 I like how you used the repeater, keeps things clean & compact.
Haskell!
Go (with bonus diamond of diamonds) playground link
Woah that's cool! I wanted to see what your diamond of diamonds looked like!
Thought I'd paste in the medium sized one, and let people go to the playground for the big one!
JS ❤️
BASH
Ruby
I didn’t follow the fine print so I’m not sure this totally fits the spec now that I’m reading more carefully.
I’ll be more careful tomorrow 😄
Ruby solution
Python
def diamond(): num = 9 for i in range(1, num+1): i = i - (num//2 +1) if i < 0: i = -i print(" " * i + "*" * (num - i*2) + " "*i) diamond()The shortest one by far
It's also fast.
ReasonML / OCaml
Runnable example: sketch.sh/s/RvRBbbn6iqnEIumBYs7UwE/
My solution for Swift :
Erlang
Javascript
You can change the characters which are considered blank and full to create different effects.
normal output -
with blank="*" and full="@" -
If you mess with the fill/blank values, you get some nice art -
Did this in rust too:
On invalid input, it returns -
PHP
Just submitted my kata. <3 codewars.
Start from the middle, and go on appending stars to the top and bottom respectively.
Python:
Gave it a try in Python. Not exactly as required since the diamond is printed on-the-fly, but I think it shows the main idea to create every line one after the other. Could also be stored in a string and then returned...
Too late but here it is anyway...
PHP:
Dirty Nim, planning to rewriting. :)
I would like to add:
1) Making
str.centerdo some of the dirty work2) Using ranges (and
chain) to iterate up and down instead of keeping a state onnumIt might be more readable to have two loops instead of using
chainbut I likechaining more because I don't need to repeat theprintIs this fast too?
I wouldn't worry about it too much, since
printrequires IO, it is by far the bottleneck.For the rest of the utilities that I used:
range,chain, andstr.center: they are all implemented inCif you are using the standardCPython(should be fast).To avoid the IO, let's compare the two functions as generators of strings (I replaced the
printwithyield (('*' * i).center(n))for both my implementation and Nicks:Seems like mine is slower than Nicks.
However, on my machine, a single print statement takes about 4.17us, which is almost as long as
diamond(11)takes without any prints!Haskell
Playing with StringBuilder on C#
And Visual Basic.NET
JS
Here's something with C++ (My personal favourite)
Clojure:
as pseudocode:
JS
Here my solution: form the upper side and reuse it.
Assuming string concatenation has linear execution time, this solution should be O(middle*num). Please correct me if I'm wrong
This took me longer than it should have. But I haven't worked with R in almost 2 years. Sure you could do it more efficiently with just a loop, but I learned some stuff about concatenating matrices to strings in R this way so I call it a win.
R:
Let's go functional in Perl! (Tests included).
Python
C# Just two main loops to print upper and lower part. One loop to calculate no of rows
ruby diamonds? Okay!
Another 🚀
Python
deviated from the spec in one specific way where I don't return null if a an even number or negative number is provided but instead throw an error.
I feel however this gives more information to the user.
Rust
JavaScript
SQL (Postgres)
A bit late, but with functional flavoured C#
Extremely late to the party but here's my solution in JS:
Dart
My solution using Python :)
Ruby
Just used some for loops to print all of the asterisks, after doing a check for over 0 and odd, and added some css to make the shape of a diamond.
Codepen
The CSS making the asterisks look like a diamond
Powershell
It will automatically center to the specified line width, and requires that the line be at least as wide as the diamond itself.
David F.
JS
Here is my simple diamond solution with Python:
Sorry for that (JS)
one line functional python, why I dunno.
No one will see this but I spent a couple of hours trying to figure it out:
Very late to the party here, but wanted to post another python solution.
Takes advantage of using string formatting to center the text, simplifying the code, also using chain from itertools to stack to range functions together.
C++
if (middleRow % 2 != 0 && middleRow > 0) {
My solution in js
Implemented this in rust with some tests. I am still learning and got a lot of experimentation done. Idk how much it matters in this case but I tried pre-allocating capacities for any vectors or strings.
At first I used modulo to get uneven numbers in the for loop but I got stuck doing it.
Fond a solutuion here in the comments of a guy using abs-values, that inspired me to instead only create the diamond up to its mid-row and then reflect it around that row.
Could maybe improve and use iterators instead of for-loop, idk?
with.capacity(), seems to take usize only, some improvement could be done here, for example I convert to usize for each capacity call.
Adding the padding at the end of a line isnt really neccessary?
Python :
Ruby Language Version
output
My go exercise two
I didn't find any good solution to abs integer in go :(
Progress 4GL solution:
Code in the ABL Dojo here
Couldnt find java one here. so uploading mine (suggestions are welcome)
if (base % 2 != 0 && base>0) {
int spaceDiff = (base / 2);
int star, row, order = 2;
// upper and middle
for (row = 0; row < base; row++) {
for (int space = spaceDiff; space > order - 2; space--) {
System.out.print(" ");
}
++order;
for (star = 0; star <= row; star++) {
System.out.print("");
}
System.out.println();
++row;
}
//bottom
order = spaceDiff;
for (row = base - 2; row > 0; row--) {
for (int space = order; space < spaceDiff + 1; space++) {
System.out.print(" ");
}
--order;
for (star = row; star > 0; star--) {
System.out.print("");
}
System.out.println();
--row;
}
}
JS
Now with contrast, invertability, custom strings and other completely unnecessary bells and whistles...
Nice one!
That's amazing >_<
Ahh you are 100% correct! I was confusing myself with Natural Numbers (which 0 is NOT), but that's unrelated to even/odd!
Good call out!
JavaScript
Late to the game here, but here you go, a JS implementation.
WOW! 😍
Javascript ans.
Javascript