# Format a US address

Your task is to format an address given in all lowercase to a friendlier format. Here's the catch, no regexes.

Addresses will be given in the following format:

123 serpentine pl ne shoreline wa 98199

The expected output is the following: (notice the period and commas)

123 Serpentine Pl. NE, Shoreline WA, 98199

Formatting Rules

• Cardinal directions should be capitalized, e.g. "e" --> "E", "nw" --> "NW".

• Abbreviations for streets, avenues, etc. should have the first letter capitalized with the abbr. followed by a period (".") e.g "st" --> "St.", "ave" --> "Ave.".

• State abbreviation should be in all caps

• A comma is placed after each section. i.e. after the street address and state and city.

• Capitalize the city and street/avenue/place.

EDIT: Addresses will always be given in the above format except with or without a cardinal direction.

Your code should also be able to handle "st" and "ave". The input is given through stdin. This is code-golf so the shortest code in bytes wins.

• Please provide an explanation of the formatting rules that should be used. It's not at all obvious from your example why "ne" and "wa" should be fully capitalized and followed by commas, while "pl" should have only the first letter capitalized and be followed by a period. – Ilmari Karonen Mar 26 '14 at 4:43
• Could you please provide a full list of st ave pl things? – mniip Mar 26 '14 at 7:00
• Also, will addresses always have this form with all the components <number> <street> <st/ave/pl> <direction> <city> <state> <zip>? Or may parts be omitted (e.g. can the address not have a St/Ave/Pl postfix, or a cardinal direction). – CompuChip Mar 26 '14 at 7:08
• The US Postal Service prefers no punctuation except for the hyphen in 9-digit zip codes and, all caps: pe.usps.gov/text/pub28/welcome.htm – Glenn Randers-Pehrson Mar 26 '14 at 17:03
• There are a lot more possible ways to enter in the given addresses - and a lot more possible variations in addresses - than is covered here. For example: 123 Serpentine Place NE, Shoreline Washington 98199 or 123 Serpentine Pl NE, Apartment 6, Shoreline Wa 98199 or 123 Serpentine Pl, 98199. How do we handle those, or are we to only expect addresses strictly in the formats already given without any more or less detail? – Iszi Mar 26 '14 at 20:07

# Perl 6: ??? characters

The simplest Perl 6 solution is probably: (61 characters)

$/=get.wordcase.words;"$0 $1$2. $3.uc(),$4 $5.uc(),$6".say


Unfortunately, I don't feel comfortable using this, since .wordcase and .words are both implemented internally using regexes. Thus: (also, oddly, 61 characters)

$/=get.split(' ')».tc;"$0 $1$2. $3.uc(),$4 $5.uc(),$6".say


BUT this only handles the specific address given in the problem. Consider:

42 awesome ln dogeland hi 96899


I see this as valid under to be formatted given the rules above, and this should be formatted as 42 Awesome Ln., Dogeland HI, 96899 rather than 42 Awesome Ln. DOGELAND, Hi 96899,. So let's fix the case that a cardinal direction isn't included: (136 characters)

my@a=get.split(" ")».tc;@a[3].=uc if @a[3] eq tc any "n","s","" X~ "e","w","";@a[2]~=".";say "@a[0..*-4], @a[*-3] @a[*-2].uc(), @a[*-1]"


# Lua - 462

_=_G d={n=_,nw=_,sw=_,s=_,se=_,e=_,ne=_,al=_,ak=_,az=_,ar=_,ca=_,co=_,ct=_,de=_,dc=_,fl=_,ga=_,hi=_,id=_,il=_,["in"]=_,ia=_,ks=_,ky=_,la=_,me=_,md=_,ma=_,mi=_,mn=_,ms=_,mo=_,mt=_,nv=_,nh=_,nj=_,nm=_,ny=_,nd=_,oh=_,ok=_,["or"]=_,pa=_,ri=_,sc=_,sd=_,tn=_,tx=_,ut=_,vt=_,va=_,wa=_,wv=_,wi=_,wy=_}l={pl=_,st=_,ave=_,hw=_}print((io.read"*a":gsub("%w+",function(x)if d[x]then return x:upper()..","end return x:sub(1,1):upper()..x:sub(2):lower()..(l[x]and"."or"")end)))


The first is a list of states and directions, the second is a list of places.
One might argue that gsub is using regular expressions, but lua uses patterns, that are close, but not exactly are regexes. They cannot match regular languages and don't even have a proper Klenee star.

Example:

 $lua % <<< '123 serpentine pl ne shoreline wa 98199' 123 Serpentine Pl. NE, Shoreline WA, 98199  # Javascript b="123 serpentine pl ne shoreline wa 98199".split(" "); c=[]; cap = function(l){var code=parseInt(l.charCodeAt(0));if(code>=97&&code<=122){l=String.fromCharCode(code-32);}return l;} c[0]=b[0]; c[6]=b[6]; b.forEach(function(txt,index){ tx=txt.split(""); switch(index){ case 1:case 4:tx[0]=cap(tx[0]);c[index]=tx.join("");break; case 2:case 3:case 5:tx.forEach(function(t,idx){ tx[idx]=cap(t); }); c[index]=tx.join(""); break; } }); //now output=c[0]+" "+c[1]+" "+c[2]+". "+c[3]+", "+c[4]+" "+c[5]+", "+c[6];  # Python3 137 122 i=input().split() c=lambda x:x.capitalize() print(i[0],c(i[1]),c(i[2])+".",i[3].upper()+",",c(i[4]),i[5].upper()+",",i[6])  >python main.py 123 serpentine pl ne shoreline wa 98199 #Pasted 123 Serpentine Pl. NE, Shoreline WA, 98199 #Output >  • I think using input() would give you a lower char count (you don't need sys) and it would fit the rules better. ("The input is given through stdin.") – user12205 Apr 1 '14 at 8:04 # Python2 (based on other python3 answer) i=raw_input().split() i=map(lambda x:x.capitalize(),i) print " ".join((i[0],i[1],i[2]+".",i[3].upper()+",",i[4] ,i[5].upper()+",",i[6]))  running in Windows cmd C:\Python27>python main.py 123 serpentine pl ne shoreline wa 98199 #Pasted 123 Serpentine Pl. NE, Shoreline WA, 98199 #Output  # Powershell v4 $h=Read-Host
$i=(Get-Culture).TextInfo.ToTitleCase($h).Split()
($i[0..2 ] -join " ")+". "+$i[-4].ToUpper()+", "+$i[-3]+" "+$i[-2].ToUpper()+",",\$i[-1]


running

C:\>powershell .\address.ps1
123 serpentine pl ne shoreline wa 98199 #Pasted
123 Serpentine Pl. NE, Shoreline WA, 98199 #Output