This page compares the YAMLScript code for the Rosetta Code task '99-bottles-of-beer' with code from other Rosetta Code Languages.
Click on the ‣ arrow for a language below to expand its code.
This Markdown page was generated by this YAMLScript program.
About Task '99-bottles-of-beer'
;Task: Display the complete lyrics for the song: '''99 Bottles of Beer on the Wall'''.
;The beer song: The lyrics follow this form:
::: 99 bottles of beer on the wall
::: 99 bottles of beer
::: Take one down, pass it around
::: 98 bottles of beer on the wall
::: 98 bottles of beer on the wall
::: 98 bottles of beer
::: Take one down, pass it around
::: 97 bottles of beer on the wall
... and so on, until reaching '''0''' (zero).
Grammatical support for ''1 bottle of beer'' is optional.
As with any puzzle, try to do it in as creative/concise/comical a way as possible (simple, obvious solutions allowed, too).
{{Template:Strings}}
;See also:
- http://99-bottles-of-beer.net/
- [[:Category:99_Bottles_of_Beer]]
- [[:Category:Programming language families]]
- [https://en.wikipedia.org/wiki/99_Bottles_of_Beer Wikipedia 99 bottles of beer]
YAMLScript (15 lines)
!yamlscript/v0
defn main(number=99):
each num (number .. 1):
say: |
$bottles(num) of beer on the wall,
$bottles(num) of beer.
Take one down, pass it around.
$bottles(num.--) of beer on the wall.
defn bottles(n):
condp eq n:
0 :: No more bottles
1 :: 1 bottle
else : "$n bottles"The Exercism Languages
8th (12 lines)
[
( "Just one more bottle of beer on the wall, one bottle of beer.\n" . ) ,
( I dup "%d bottles of beer on the wall, %d bottles of beer.\n" s:strfmt . )
] constant lyrics
: app:main
(
dup lyrics [2,99] rot ' n:cmp a:pigeon w:exec
n:1- "Take one down, pass it around, %d bottles of beer on the wall.\n\n" s:strfmt .
) 1 99 loop-
"No more bottles of beer on the wall, no more bottles of beer.\n" . ;
ABAP (18 lines)
REPORT YCL_99_BOTTLES.
DATA it_99_bottles TYPE TABLE OF string WITH EMPTY KEY.
DATA(cr_lf) = cl_abap_char_utilities=>cr_lf.
it_99_bottles = VALUE #(
FOR i = 99 THEN i - 1 UNTIL i = 0 ( COND string( LET lv = ( i - 1 )
lr = i && | bottles of beer on the wall|
&& cr_lf
&& i && | bottles of beer|
&& cr_lf
&& |Take one down, pass it around|
&& cr_lf
&& lv && | bottles of beer on the wall|
&& cr_lf IN WHEN 1 = 1 THEN lr )
)
).
cl_demo_output=>write( it_99_bottles ).
cl_demo_output=>display( ).AWK (21 lines)
# usage: gawk -v i=6 -f beersong.awk
function bb(n) {
b = " bottles of beer"
if( n==1 ) { sub("s","",b) }
if( n==0 ) { n="No more" }
return n b
}
BEGIN {
if( !i ) { i = 99 }
ow = "on the wall"
td = "Take one down, pass it around."
print "The beersong:\n"
while (i > 0) {
printf( "%s %s,\n%s.\n%s\n%s %s.\n\n",
bb(i), ow, bb(i), td, bb(--i), ow )
if( i==1 ) sub( "one","it", td )
}
print "Go to the store and buy some more!"
}C (17 lines)
#include <stdio.h>
int main(int argc, char *argv[])
{
if(argc == 99)
return 99;
if(argv[0] != NULL){
argv[0] = NULL;
argc = 0;
}
argc = main(argc + 1, argv);
printf("%d bottle%c of beer on the wall\n", argc, argc == 1?'\0': 's');
printf("%d bottle%c of beer\n", argc, argc == 1?'\0': 's');
printf("Take one down, pass it around\n");
printf("%d bottle%c of beer on the wall\n\n", argc - 1, (argc - 1) == 1?'\0': 's');
return argc - 1;
}C++ (20 lines)
#include <iostream>
using namespace std;
void rec(int bottles)
{
if ( bottles!=0)
{
cout << bottles << " bottles of beer on the wall" << endl;
cout << bottles << " bottles of beer" << endl;
cout << "Take one down, pass it around" << endl;
cout << --bottles << " bottles of beer on the wall\n" << endl;
rec(bottles);
}
}
int main()
{
rec(99);
system("pause");
return 0;
}ColdFusion (9 lines)
<cfoutput>
<cfloop index="x" from="99" to="0" step="-1">
<cfset plur = iif(x is 1,"",DE("s"))>
#x# bottle#plur# of beer on the wall<br>
#x# bottle#plur# of beer<br>
Take one down, pass it around<br>
#iif(x is 1,DE("No more"),"x-1")# bottle#iif(x is 2,"",DE("s"))# of beer on the wall<br><br>
</cfloop>
</cfoutput>Clojure (13 lines)
(defn paragraph [num]
(str num " bottles of beer on the wall\n"
num " bottles of beer\n"
"Take one down, pass it around\n"
(dec num) " bottles of beer on the wall.\n"))
(defn lyrics []
(let [numbers (range 99 0 -1)
paragraphs (map paragraph numbers)]
(clojure.string/join "\n" paragraphs)))
(print (lyrics))COBOL (16 lines)
program-id. ninety-nine.
data division.
working-storage section.
01 cnt pic 99.
procedure division.
perform varying cnt from 99 by -1 until cnt < 1
display cnt " bottles of beer on the wall"
display cnt " bottles of beer"
display "Take one down, pass it around"
subtract 1 from cnt
display cnt " bottles of beer on the wall"
add 1 to cnt
display space
end-perform.CoffeeScript (4 lines)
for j in [99..1]
x=''
x += [j,j-1,'\nTake one down, pass it around\n'," bottles of beer",' on the wall\n'][i] for i in [0,3,4,0,3,2,1,3,4]
console.log x.replace /(1.+)s/g, '$1'C-sharp (12 lines)
public static void BottlesSong(int numberOfBottles)
{
if (numberOfBottles > 0)
{
Console.WriteLine("{0} bottles of beer on the wall", numberOfBottles);
Console.WriteLine("{0} bottles of beer ", numberOfBottles);
Console.WriteLine("Take one down, pass it around");
Console.WriteLine("{0} bottles of beer ", numberOfBottles - 1);
Console.WriteLine();
BottlesSong(--numberOfBottles);
}
}Crystal (7 lines)
99.downto(1) do |n|
puts "#{n} bottle#{n > 1 ? "s" : ""} of beer on the wall"
puts "#{n} bottle#{n > 1 ? "s" : ""} of beer"
puts "Take one down, pass it around"
puts "#{n-1} bottle#{n > 2 ? "s" : ""} of beer on the wall\n\n" if n > 1
end
puts "No more bottles of beer on the wall"D (21 lines)
module bottles;
template BeerSong(int Bottles)
{
static if (Bottles == 1)
{
enum BeerSong = "1 bottle of beer on the wall\n" ~
"1 bottle of beer\ntake it down, pass it around\n" ~ "
no more bottles of beer on the wall\n";
}
else
{
enum BeerSong = Bottles.stringof ~ " bottles of beer on the wall\n" ~
Bottles.stringof ~ " bottles of beer\ntake it down, pass it around\n" ~
BeerSong!(Bottles-1);
}
}
pragma(msg,BeerSong!99);
void main(){}Dart (61 lines)
main() {
BeerSong beerSong = BeerSong();
//pass a 'starting point' and 'end point' as parameters respectively
String printTheLyrics = beerSong.recite(99, 1).join('\n');
print(printTheLyrics);
}
class Song {
String bottleOnTheWall(int index) {
String bottleOnTheWallText =
'$index bottles of beer on the wall, $index bottles of beer,';
return bottleOnTheWallText;
}
String bottleTakenDown(int index) {
String englishGrammar = (index >= 2) ? 'bottle' : 'bottles';
String bottleTakenDownText =
'Take one down and pass it around, ${index - 1} $englishGrammar of beer on the wall.';
return bottleTakenDownText;
}
}
class BeerSong extends Song {
@override
String bottleOnTheWall(int index) {
String originalText = super.bottleOnTheWall(index);
if (index < 2) {
String bottleOnTheWallText =
'$index bottle of beer on the wall, $index bottle of beer,';
return bottleOnTheWallText;
}
return originalText;
}
@override
String bottleTakenDown(int index) {
if (index < 2) {
String bottleTakenDownText =
'Take it down and pass it around, no more bottles of beer on the wall.';
return bottleTakenDownText;
}
String originalText = super.bottleTakenDown(index);
return originalText;
}
List<String> recite(int actualBottleOnTheWall, int remainingBottleOnTheWall) {
List<String> theLyrics = [];
for (int index = actualBottleOnTheWall;
index >= remainingBottleOnTheWall;
index--) {
String onTheWall = bottleOnTheWall(index);
String takenDown = bottleTakenDown(index);
theLyrics.add(onTheWall);
theLyrics.add(takenDown);
theLyrics.add('');
}
return theLyrics;
}
}
}Elixir (16 lines)
defmodule Bottles do
def run do
Enum.each 99..1, fn idx ->
IO.puts "#{idx} bottle#{plural(idx)} of beer on the wall"
IO.puts "#{idx} bottle#{plural(idx)} of beer"
IO.puts "Take one down, pass it around"
IO.puts "#{idx - 1} bottle#{plural(idx-1)} of beer on the wall"
IO.puts ""
end
end
def plural(1), do: ""
def plural(num), do: "s"
end
Bottles.runElm (27 lines)
module Main exposing (main)
import Html
main =
List.range 1 100
|> List.reverse
|> List.map
(\n ->
let
nString =
String.fromInt n
n1String =
String.fromInt (n - 1)
in
[ nString ++ " bottles of beer on the wall"
, nString ++ " bottles of beer"
, "Take one down, pass it around"
, n1String ++ " bottles of beer on the wall"
]
|> List.map Html.text
|> List.intersperse (Html.br [] [])
|> Html.p []
)
|> Html.div []Emacs-Lisp (7 lines)
(let ((i 99))
(while (> i 0)
(message "%d bottles of beer on the wall" i)
(message "%d bottles of beer" i)
(message "Take one down, pass it around")
(message "%d bottles of beer on the wall" (1- i))
(setq i (1- i))))Erlang (39 lines)
-module(beersong).
-export([sing/0]).
-define(TEMPLATE_0, "~s of beer on the wall, ~s of beer.~nGo to the store and buy some more, 99
bottles of beer on the wall.~n").
-define(TEMPLATE_N, "~s of beer on the wall, ~s of beer.~nTake one down and pass it around, ~s of
beer on the wall.~n~n").
create_verse(0) -> {0, io_lib:format(?TEMPLATE_0, phrase(0))};
create_verse(Bottle) -> {Bottle, io_lib:format(?TEMPLATE_N, phrase(Bottle))}.
phrase(0) -> ["No more bottles", "no more bottles"];
phrase(1) -> ["1 bottle", "1 bottle", "no more bottles"];
phrase(2) -> ["2 bottles", "2 bottles", "1 bottle"];
phrase(Bottle) -> lists:duplicate(2, integer_to_list(Bottle) ++ " bottles") ++
[integer_to_list(Bottle-1) ++ " bottles"].
bottles() -> lists:reverse(lists:seq(0,99)).
sing() ->
lists:foreach(fun spawn_singer/1, bottles()),
sing_verse(99).
spawn_singer(Bottle) ->
Pid = self(),
spawn(fun() -> Pid ! create_verse(Bottle) end).
sing_verse(Bottle) ->
receive
{_, Verse} when Bottle == 0 ->
io:format(Verse);
{N, Verse} when Bottle == N ->
io:format(Verse),
sing_verse(Bottle-1)
after
3000 ->
io:format("Verse not received - re-starting singer~n"),
spawn_singer(Bottle),
sing_verse(Bottle)
end.Euphoria (20 lines)
-- yet another version:
include std/console.e
object stanza = {
"[] bottles of beer on the wall,",
"[] bottles of beer,",
"take one down, and pass it around,"
}
object bottles = 99
loop do
display(stanza[1],bottles)
display(stanza[2],bottles)
display(stanza[3])
bottles -= 1
display(stanza[1]&"\n",{bottles})
until bottles = 0
end loopFortran (132 lines)
module song_typedefs
implicit none
private ! all
public :: TBottles
type, abstract :: TContainer
integer :: quantity
contains
! deferred method i.e. abstract method = must be overridden in extended type
procedure(take_one), deferred, pass :: take_one
procedure(show_quantity), deferred, pass :: show_quantity
end type TContainer
abstract interface
subroutine take_one(this)
import TContainer
implicit none
class(TContainer) :: this
end subroutine take_one
subroutine show_quantity(this)
import TContainer
implicit none
class(TContainer) :: this
end subroutine show_quantity
end interface
! extended derived type
type, extends(TContainer) :: TBottles
contains
procedure, pass :: take_one => take_one_bottle
procedure, pass :: show_quantity => show_bottles
final :: finalize_bottles
end type TBottles
contains
subroutine show_bottles(this)
implicit none
class(TBottles) :: this
! integer :: show_bottles
character(len=*), parameter :: bw0 = "No more bottles of beer on the wall,"
character(len=*), parameter :: bwx = "bottles of beer on the wall,"
character(len=*), parameter :: bw1 = "bottle of beer on the wall,"
character(len=*), parameter :: bb0 = "no more bottles of beer."
character(len=*), parameter :: bbx = "bottles of beer."
character(len=*), parameter :: bb1 = "bottle of beer."
character(len=*), parameter :: fmtxdd = "(I2,1X,A28,1X,I2,1X,A16)"
character(len=*), parameter :: fmtxd = "(I1,1X,A28,1X,I1,1X,A16)"
character(len=*), parameter :: fmt1 = "(I1,1X,A27,1X,I1,1X,A15)"
character(len=*), parameter :: fmt0 = "(A36,1X,A24)"
select case (this % quantity)
case (10:)
write(*,fmtxdd) this % quantity, bwx, this % quantity, bbx
case (2:9)
write(*,fmtxd) this % quantity, bwx, this % quantity, bbx
case (1)
write(*,fmt1) this % quantity, bw1, this % quantity, bb1
case (0)
write(*,*)
write(*,fmt0) bw0, bb0
case default
write(*,*)"Warning! Number of bottles exception, error 42. STOP"
stop
end select
! show_bottles = this % quantity
end subroutine show_bottles
subroutine take_one_bottle(this) ! bind(c, name='take_one_bottle')
implicit none
class(TBottles) :: this
! integer :: take_one_bottle
character(len=*), parameter :: t1 = "Take one down and pass it around,"
character(len=*), parameter :: remx = "bottles of beer on the wall."
character(len=*), parameter :: rem1 = "bottle of beer on the wall."
character(len=*), parameter :: rem0 = "no more bottles of beer on the wall."
character(len=*), parameter :: fmtx = "(A33,1X,I2,1X,A28)"
character(len=*), parameter :: fmt1 = "(A33,1X,I2,1X,A27)"
character(len=*), parameter :: fmt0 = "(A33,1X,A36)"
this % quantity = this % quantity -1
select case (this%quantity)
case (2:)
write(*,fmtx) t1, this%quantity, remx
case (1)
write(*,fmt1) t1, this%quantity, rem1
case (0)
write(*,fmt0) t1, rem0
case (-1)
write(*,'(A66)') "Go to the store and buy some more, 99 bottles of beer on the wall."
case default
write(*,*)"Warning! Number of bottles exception, error 42. STOP"
stop
end select
end subroutine take_one_bottle
subroutine finalize_bottles(bottles)
implicit none
type(TBottles) :: bottles
! here can be more code
end subroutine finalize_bottles
end module song_typedefs
!-----------------------------------------------------------------------
!Main program
!-----------------------------------------------------------------------
program bottles_song
use song_typedefs
implicit none
integer, parameter :: MAGIC_NUMBER = 99
type(TBottles), target :: BTLS
BTLS = TBottles(MAGIC_NUMBER)
call make_song(BTLS)
contains
subroutine make_song(bottles)
type(TBottles) :: bottles
do while(bottles%quantity >= 0)
call bottles%show_quantity()
call bottles%take_one()
enddo
end subroutine make_song
end program bottles_song
F-Sharp (12 lines)
#light
let rec bottles n =
let (before, after) = match n with
| 1 -> ("bottle", "bottles")
| 2 -> ("bottles", "bottle")
| n -> ("bottles", "bottles")
printfn "%d %s of beer on the wall" n before
printfn "%d %s of beer" n before
printfn "Take one down, pass it around"
printfn "%d %s of beer on the wall\n" (n - 1) after
if n > 1 then
bottles (n - 1)Go (80 lines)
package main
import (
"fmt"
"math/rand"
"strings"
"time"
)
func main() {
rand.Seed(time.Now().UnixNano())
for i := 99; i > 0; i-- {
fmt.Printf("%s %s %s\n",
slur(numberName(i), i),
pluralizeFirst(slur("bottle of", i), i),
slur("beer on the wall", i))
fmt.Printf("%s %s %s\n",
slur(numberName(i), i),
pluralizeFirst(slur("bottle of", i), i),
slur("beer", i))
fmt.Printf("%s %s %s\n",
slur("take one", i),
slur("down", i),
slur("pass it around", i))
fmt.Printf("%s %s %s\n",
slur(numberName(i-1), i),
pluralizeFirst(slur("bottle of", i), i-1),
slur("beer on the wall", i))
}
}
// adapted from Number names task
func numberName(n int) string {
switch {
case n < 0:
case n < 20:
return small[n]
case n < 100:
t := tens[n/10]
s := n % 10
if s > 0 {
t += " " + small[s]
}
return t
}
return ""
}
var small = []string{"no", "one", "two", "three", "four", "five", "six",
"seven", "eight", "nine", "ten", "eleven", "twelve", "thirteen",
"fourteen", "fifteen", "sixteen", "seventeen", "eighteen", "nineteen"}
var tens = []string{"ones", "ten", "twenty", "thirty", "forty",
"fifty", "sixty", "seventy", "eighty", "ninety"}
// pluralize first word of s by adding an s, but only if n is not 1.
func pluralizeFirst(s string, n int) string {
if n == 1 {
return s
}
w := strings.Fields(s)
w[0] += "s"
return strings.Join(w, " ")
}
// p is string to slur, d is drunkenness, from 0 to 99
func slur(p string, d int) string {
// shuffle only interior letters
a := []byte(p[1 : len(p)-1])
// adapted from Knuth shuffle task.
// shuffle letters with probability d/100.
for i := len(a) - 1; i >= 1; i-- {
if rand.Intn(100) >= d {
j := rand.Intn(i + 1)
a[i], a[j] = a[j], a[i]
}
}
// condense spaces
w := strings.Fields(p[:1] + string(a) + p[len(p)-1:])
return strings.Join(w, " ")
}Groovy (10 lines)
def bottles = { "${it==0 ? 'No more' : it} bottle${it==1 ? '' : 's' }" }
99.downto(1) { i ->
print """
${bottles(i)} of beer on the wall
${bottles(i)} of beer
Take one down, pass it around
${bottles(i-1)} of beer on the wall
"""
}Haskell (28 lines)
{-# LANGUAGE TemplateHaskell #-}
-- build with "ghc --make beer.hs"
module Main where
import Language.Haskell.TH
import Control.Monad.Writer
-- This is calculated at compile time, and is equivalent to
-- songString = "99 bottles of beer on the wall\n99 bottles..."
songString =
$(let
sing = tell -- we can't sing very well...
someBottles 1 = "1 bottle of beer "
someBottles n = show n ++ " bottles of beer "
bottlesOfBeer n = (someBottles n ++)
verse n = do
sing $ n `bottlesOfBeer` "on the wall\n"
sing $ n `bottlesOfBeer` "\n"
sing $ "Take one down, pass it around\n"
sing $ (n - 1) `bottlesOfBeer` "on the wall\n\n"
song = execWriter $ mapM_ verse [99,98..1]
in return $ LitE $ StringL $ song)
main = putStr songStringJava (41 lines)
import java.awt.BorderLayout;
import java.awt.event.ActionEvent;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JOptionPane;
import javax.swing.JTextArea;
public class Beer extends JFrame {
private int x;
private JTextArea text;
public static void main(String[] args) {
new Beer().setVisible(true);
}
public Beer() {
x = 99;
JButton take = new JButton("Take one down, pass it around");
take.addActionListener(this::onTakeClick);
text = new JTextArea(4, 30);
text.setText(x + " bottles of beer on the wall\n" + x + " bottles of beer");
text.setEditable(false);
setLayout(new BorderLayout());
add(text, BorderLayout.CENTER);
add(take, BorderLayout.PAGE_END);
pack();
setLocationRelativeTo(null);
setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
}
private void onTakeClick(ActionEvent event) {
JOptionPane.showMessageDialog(null, --x + " bottles of beer on the wall");
text.setText(x + " bottles of beer on the wall\n" + x + " bottles of beer");
if (x == 0) {
dispose();
}
}
}JavaScript (25 lines)
function Bottles(count) {
this.count = count || 99;
}
Bottles.prototype.take = function() {
var verse = [
this.count + " bottles of beer on the wall,",
this.count + " bottles of beer!",
"Take one down, pass it around",
(this.count - 1) + " bottles of beer on the wall!"
].join("\n");
console.log(verse);
this.count--;
};
Bottles.prototype.sing = function() {
while (this.count) {
this.take();
}
};
var bar = new Bottles(99);
bar.sing();Jq (17 lines)
$ jq -n -r -f 99_bottles.jq
...
2 bottles of beer on the wall
2 bottles of beer
Take one down, pass it around
2 bottles of beer on the wall
1 bottles of beer on the wall
1 bottles of beer
Take one down, pass it around
1 bottles of beer on the wall
0 bottles of beer on the wall
0 bottles of beer
Take one down, pass it around
0 bottles of beer on the wallJulia (12 lines)
bottles(n) = n==0 ? "No more bottles" :
n==1 ? "1 bottle" :
"$n bottles"
for n = 99:-1:1
println("""
$(bottles(n)) of beer on the wall
$(bottles(n)) of beer
Take one down, pass it around
$(bottles(n-1)) of beer on the wall
""")
endKotlin (8 lines)
fun main(args: Array<String>) {
for (i in 99.downTo(1)) {
println("$i bottles of beer on the wall")
println("$i bottles of beer")
println("Take one down, pass it around")
}
println("No more bottles of beer on the wall!")
}Lua (10 lines)
verse = [[%i bottle%s of beer on the wall
%i bottle%s of beer
Take one down, pass it around
%i bottle%s of beer on the wall
]]
function suffix(i) return i ~= 1 and 's' or '' end
for i = 99, 1, -1 do
print(verse:format(i, suffix(i), i, suffix(i), i-1, suffix(i-1)))
endMIPS-Assembly (77 lines)
##################################
# 99 bottles of beer on the wall #
# MIPS Assembly targeting MARS #
# By Keith Stellyes #
# August 24, 2016 #
##################################
#It is simple, a loop that goes as follows:
#if accumulator is not 1:
#PRINT INTEGER: accumulator
#PRINT lyrica
#PRINT INTEGER: accumulator
#PRINT lyricb
#PRINT INTEGER: accumulator
#PRINT lyricc
#DECREMENT accumulator
#else:
#PRINT FINAL LYRICS
.data
lyrica: .asciiz " bottles of beer on the wall, "
lyricb: " bottles of beer.\nTake one down and pass it around, "
lyricc: " bottles of beer on the wall. \n\n"
#normally, I don't like going past 80 columns, but that was done here.
# there's an argument to be had for breaking this up. I chose not to
# for simpler instructions.
final_lyrics: "1 bottle of beer on the wall, 1 bottle of beer.\nTake one down and pass it around, no more bottles of beer on the wall.\n\nNo more bottles of beer on the wall, no more bottles of beer.\nGo to the store and buy some more, 99 bottles of beer on the wall."
.text
#lw $a0,accumulator #load address of accumulator into $a0 (or is it getting val?)
li $a1,99 #set the inital value of the counter to 99
loop:
###99
li $v0, 1 #specify print integer system service
move $a0,$a1
syscall #print that integer
### bottles of beer on the wall,
la $a0,lyrica
li $v0,4
syscall
###99
li $v0, 1 #specify print integer system service
move $a0,$a1
syscall #print that integer
### bottles of beer.\n Take one down and pass it around,
la $a0,lyricb
li $v0,4
syscall
###99
li $v0, 1 #specify print integer system service
move $a0,$a1
syscall #print that integer
### "bottles of beer on the wall. \n\n"
la $a0,lyricc
li $v0,4
syscall
#decrement counter, if at 1, print the final and exit.
subi $a1,$a1,1
bne $a1,1,loop
### PRINT FINAL LYRIC, THEN TERMINATE.
final: la $a0,final_lyrics
li $v0,4
syscall
li $v0,10
syscall
Nim (21 lines)
from strutils import format
for i in countdown(99, 1):
case i
of 3..99:
echo format("""$1 bottles of beer on the wall
$1 bottles of beer
Take one down, pass it around
$2 bottles of beer on the wall""", i, i-1)
of 2:
echo format("""$1 bottles of beer on the wall
$1 bottles of beer
Take one down, pass it around
$2 bottle of beer on the wall""", i, i-1)
of 1:
echo format("""$1 bottle of beer on the wall
$1 bottle of beer
Take one down, pass it around
No more bottles of beer on the wall""", i)
else:
discardObjective-C (17 lines)
#import <Foundation/Foundation.h>
int main()
{
@autoreleasepool {
int bottles = 99;
do
{
NSLog(@"%i bottles of beer on the wall\n", bottles);
NSLog(@"%i bottles of beer\n", bottles);
NSLog(@"Take one down, pass it around\n");
NSLog(@"%i bottles of beer on the wall\n\n", --bottles);
} while (bottles > 0);
}
return 0;
}
OCaml (6 lines)
for n = 99 downto 1 do
Printf.printf "%d bottles of beer on the wall\n" n;
Printf.printf "%d bottles of beer\n" n;
Printf.printf "Take one down, pass it around\n";
Printf.printf "%d bottles of beer on the wall\n\n" (pred n);
donePerl (18 lines)
#!/usr/bin/perl -w
my $verse = <<"VERSE";
100 bottles of beer on the wall,
100 bottles of beer!
Take one down, pass it around!
99 bottles of beer on the wall!
VERSE
{
$verse =~ s/(\d+)/$1-1/ge;
$verse =~ s/\b1 bottles/1 bottle/g;
my $done = $verse =~ s/\b0 bottle/No bottles/g; # if we make this replacement, we're also done.
print $verse;
redo unless $done;
}Smalltalk (15 lines)
Smalltalk at: #sr put: 0 ; at: #s put: 0 !
sr := Dictionary new.
sr at: 0 put: ' bottle' ;
at: 1 put: ' bottles' ;
at: 2 put: ' of beer' ;
at: 3 put: ' on the wall' ;
at: 4 put: 'Take one down, pass it around' !
99 to: 0 by: -1 do: [:v | v print.
( v == 1 ) ifTrue: [ s := 0. ]
ifFalse: [ s := 1. ].
Transcript show: (sr at:s) ; show: (sr at:2) ; show: (sr at:3) ; cr.
v print.
Transcript show: (sr at:s) ; show: (sr at:2) ; cr.
(v ~~ 0) ifTrue: [ Transcript show: (sr at:4) ; cr. ].
].PHP (16 lines)
<?php
$bottles = 99;
while ($bottles > 0) {
printf(ngettext('%d bottle', '%d bottles', $bottles) . " of beer on the wall\n", $bottles); //X bottles of beer on the wall
printf(ngettext('%d bottle', '%d bottles', $bottles) . " of beer\n", $bottles); //X bottles of beer
printf("Take one down, pass it around\n"); //Take one down, pass it around
$bottles--;
if ($bottles > 0) {
printf(ngettext('%d bottle', '%d bottles', $bottles) . " of beer on the wall\n\n", $bottles); //X bottles of beer on the wall
}
}
printf('No more bottles of beer on the wall'); //No more bottles of beer on the wallPython (25 lines)
VERSE = '''\
{n} bottle{s} of beer on the wall
{n} bottle{s} of beer
Take one down, pass it around
{n_minus_1} bottle{s2} of beer on the wall
'''
for n in range(99, 0, -1):
if n == 1:
n_minus_1 = 'No more'
s = ''
s2 = 's'
elif n == 2:
n_minus_1 = n - 1;
s = 's'
s2 = ''
else:
n_minus_1 = n - 1;
s = 's'
s2 = 's'
print(VERSE.format(n=n, s=s, s2=s2, n_minus_1=n_minus_1))R (16 lines)
#a naive function to sing for N bottles of beer...
song = function(bottles){
for(i in bottles:1){ #for every integer bottles, bottles-1 ... 1
cat(bottles," bottles of beer on the wall \n",bottles," bottles of beer \nTake one down, pass it around \n",
bottles-1, " bottles of beer on the wall \n"," \n" ,sep="") #join and print the text (\n means new line)
bottles = bottles - 1 #take one down...
}
}
song(99)#play the song by calling the functionRacket (8 lines)
#lang racket
(define (sing bottles)
(define (plural n) (~a n " bottle" (if (= n 1) "" "s")))
(printf "~a of beer on the wall\n~a of beer\n~
Take one down, pass it around\n~a of beer on the wall\n\n"
(plural bottles) (plural bottles) (plural (sub1 bottles)))
(unless (= 1 bottles) (sing (sub1 bottles))))
(sing 99)Raku (18 lines)
for 99...1 -> $bottles {
sing $bottles, :wall;
sing $bottles;
say "Take one down, pass it around";
sing $bottles - 1, :wall;
say "";
}
#| Prints a verse about a certain number of beers, possibly on a wall.
sub sing(
Int $number, #= Number of bottles of beer.
Bool :$wall, #= Mention that the beers are on a wall?
) {
my $quantity = $number == 0 ?? "No more" !! $number;
my $plural = $number == 1 ?? "" !! "s";
my $location = $wall ?? " on the wall" !! "";
say "$quantity bottle$plural of beer$location"
}Red (21 lines)
w: 99
while [w][
print [
reform [
w x: either 1 < w ["bottles"] ["bottle"] y: "of beer" z: "on the wall" ","
w x y
]
]
w: w - 1
if w = 1 [remove at x length? x]
print [
"take one down pass it around, "
either 0 < w [
reform [w x y z]
][
w: false reform [
"no more bottles " y rejoin [z "."]
]
]
]
]Ruby (14 lines)
def bottles(beer, wall = false)
"#{beer>0 ? beer : "no more"} bottle#{"s" if beer!=1} of beer#{" on the wall" if wall}"
end
99.downto(0) do |remaining|
puts "#{bottles(remaining,true).capitalize}, #{bottles(remaining)}."
if remaining==0
print "Go to the store and buy some more"
remaining=100
else
print "Take one down, pass it around"
end
puts ", #{bottles(remaining-1,true)}.\n\n"
endRust (18 lines)
fn main() {
for n in (0..100).rev() {
match n {
0 => {
println!("No more bottles of beer on the wall, no more bottles of beer.");
println!("Go to the store and buy some more, 99 bottles of beer on the wall.");
},
1 => {
println!("1 bottle of beer on the wall, 1 bottle of beer.");
println!("Take one down and pass it around, no more bottles of beer on the wall.\n");
},
_ => {
println!("{0:?} bottles of beer on the wall, {0:?} bottles of beer.", n);
println!("Take one down and pass it around, {} bottles of beer on the wall.\n", n-1);
},
}
}
}Scheme (12 lines)
(define (sing)
(define (sing-to-x n)
(if (> n -1)
(begin
(display n)
(display "bottles of beer on the wall")
(newline)
(display "Take one down, pass it around")
(newline)
(sing-to-x (- n 1)))
(display "would you wanna me to sing it again?")))
(sing-to-x 99))Standard-ML (7 lines)
fun bottles 0 = ()
| bottles x = ( print (Int.toString x ^ " bottles of beer on the wall\n");
print (Int.toString x ^ " bottles of beer\n");
print "Take one down, pass it around\n";
print (Int.toString (x-1) ^ " bottles of beer on the wall\n");
bottles (x-1)
)Swift (5 lines)
for i in (1...99).reversed() {
print("\(i) bottles of beer on the wall, \(i) bottles of beer.")
let next = i == 1 ? "no" : (i-1).description
print("Take one down and pass it around, \(next) bottles of beer on the wall.")
}TypeScript (18 lines)
function beerSong(){
function nbottles(howMany:number){
return `${howMany?howMany:'no'} bottle${howMany!=1?'s':''}`;
}
let song=[];
let beer = 99;
while (beer > 0) {
song.push(`
${nbottles(beer)} of beer on the wall,
${nbottles(beer)} of beer!
Take one down, pass it around
${nbottles(--beer)} of beer on the wall
`);
}
return song.join('');
}
console.log(beerSong());Wren (6 lines)
for (i in 99...0) {
System.print("%(i) bottles of beer on the wall,")
System.print("%(i) bottles of beer,")
System.print("Take one down, pass it around,")
System.print("%(i - 1) bottles of beer on the wall.\n")
}Zig (22 lines)
const print = @import("std").debug.print;
pub fn main() void {
var i: u8 = 99;
while (i > 2) : (i-= 1) {
print(
\\{} bottles of beer on the wall, {} bottles of beer.
\\Take one down and pass it around, {} bottles of beer on the wall.
\\
\\
, .{i, i, i-1});
}
print(
\\2 bottles of beer on the wall, 2 bottles of beer.
\\Take one down and pass it around, 1 bottle of beer on the wall.
\\
\\1 bottle of beer on the wall, 1 bottle of beer.
\\Take one down and pass it around, no more bottles of beer on the wall.
\\
\\No more bottles of beer on the wall, no more bottles of beer.
\\Go to the store and buy some more, 99 bottles of beer on the wall.
, .{});
}About
YAMLScript is a relatively new programming language and this project is intended to show how things are done with it compared to some other programming languages.
When comparing these programs, keep in mind that they were all written by different people and they are not necessarily exactly equivalent.
For example, most of the YAMLScript programs are written to be runnable with:
$ ys task-name.ys
which prints the intended results.
This is not necessarily the case for the solutions in other languages. Many solutions just show the functions necessary to complete the task.
Also the line counts are not meant ot imply any superiority of a solution.
A great way to contribute to YAMLScript is to add more YAMLScript task solutions to Rosetta Code.
You can use this program to compare your solutions with others.