/* SAS program to accompany the article "Two interfaces for typing text by using a TV remote control" by Rick Wicklin, published 12SEP2018 on The DO Loop blog: https://blogs.sas.com/content/iml/2018/09/12/interfaces-remote-control-text.html This program analyzes 1000 movie titles from IMDB's list of highly ranked movies (accessed 03Sep2018). For example: https://www.imdb.com/search/title?groups=top_1000&sort=year,asc&view=simple For each movie titles, the program computes the number of arrow keys on a TV remote control (Up, Down, Left, and Right) that must be pressed in order to type title (ignoring punctuation) in the Netflix and Amazon Video interface. Both interfaces arrange letters in a grid. The Netflix interface starts with the cursor positioned on 'A' (upper left); the Amazon Video interface starts with the cursor positioned on 'Q' (upper left). */ /******************************************************/ data Movies; length Title $80; infile datalines; input; /* read one line at a time */ title = strip(_infile_); datalines; The Cabinet of Dr. Caligari The Kid Nosferatu Sherlock Jr. The Gold Rush Battleship Potemkin The General Metropolis Sunrise The Passion of Joan of Arc All Quiet on the Western Front M City Lights Dracula Frankenstein Freaks King Kong Duck Soup It Happened One Night Bride of Frankenstein The 39 Steps A Night at the Opera Modern Times Snow White and the Seven Dwarfs La Grande Illusion The Adventures of Robin Hood Bringing Up Baby The Lady Vanishes The Wizard of Oz Gone with the Wind Stagecoach Mr. Smith Goes to Washington Rebecca The Great Dictator Fantasia The Grapes of Wrath The Philadelphia Story His Girl Friday Citizen Kane The Maltese Falcon Casablanca Shadow of a Doubt Arsenic and Old Lace Double Indemnity Laura To Have and Have Not Spellbound Brief Encounter The Lost Weekend The Best Years of Our Lives It's a Wonderful Life Notorious The Big Sleep Miracle on 34th Street Out of the Past Rope The Treasure of the Sierra Madre Bicycle Thieves Key Largo The Third Man Kind Hearts and Coronets Sunset Boulevard All About Eve Rashomon Harvey A Streetcar Named Desire Strangers on a Train The African Queen The Day the Earth Stood Still Singin' in the Rain High Noon The Quiet Man Ikiru Roman Holiday Shane Stalag 17 From Here to Eternity Tokyo Story The Wages of Fear Rear Window Seven Samurai On the Waterfront Sabrina Dial M for Murder La Strada Rebel Without a Cause The Night of the Hunter East of Eden Diabolique The Ten Commandments The Searchers Giant Forbidden Planet The Killing Invasion of the Body Snatchers 12 Angry Men The Seventh Seal The Bridge on the River Kwai Paths of Glory Witness for the Prosecution Wild Strawberries Throne of Blood The Nights of Cabiria Touch of Evil Vertigo Cat on a Hot Tin Roof The Hidden Fortress Some Like It Hot North by Northwest Ben-Hur Rio Bravo Anatomy of a Murder The 400 Blows Psycho Spartacus The Magnificent Seven The Apartment The Time Machine La Dolce Vita Breathless Peeping Tom Breakfast at Tiffany's West Side Story Judgment at Nuremberg The Guns of Navarone Yojimbo The Hustler To Kill a Mockingbird Lolita Lawrence of Arabia What Ever Happened to Baby Jane? The Longest Day The Man Who Shot Liberty Valance The Manchurian Candidate Jules and Jim The Birds The Great Escape 8 1/2 Charade Mary Poppins A Fistful of Dollars Dr. Strangelove or: How I Learned to Stop Worrying and Love the Bomb Goldfinger My Fair Lady A Hard Day's Night Zulu The Sound of Music For a Few Dollars More Doctor Zhivago Repulsion The Good, the Bad and the Ugly Blow-Up Persona Andrei Rublev Who's Afraid of Virginia Woolf? A Man for All Seasons The Battle of Algiers The Graduate The Jungle Book Cool Hand Luke The Dirty Dozen Bonnie and Clyde In the Heat of the Night Guess Who's Coming to Dinner Belle de Jour The Producers Le Samouraï 2001: A Space Odyssey Once Upon a Time in the West Rosemary's Baby Planet of the Apes Night of the Living Dead Romeo and Juliet Where Eagles Dare The Lion in Winter The Odd Couple Butch Cassidy and the Sundance Kid Midnight Cowboy The Wild Bunch Kelly's Heroes MASH Patton Little Big Man A Clockwork Orange Dirty Harry Willy Wonka & the Chocolate Factory The French Connection Solaris The Last Picture Show Fiddler on the Roof Harold and Maude Duck, You Sucker And Now for Something Completely Different The Godfather Deliverance Cabaret Sleuth Aguirre, the Wrath of God The Discreet Charm of the Bourgeoisie Papillon The Exorcist The Sting The Wicker Man The Holy Mountain Enter the Dragon Serpico Robin Hood Badlands High Plains Drifter Paper Moon The Day of the Jackal Amarcord The Godfather: Part II Blazing Saddles Young Frankenstein Chinatown The Conversation The Mirror Jaws One Flew Over the Cuckoo's Nest Monty Python and the Holy Grail Barry Lyndon Dog Day Afternoon Deep Red The Man Who Would Be King Love and Death Sholay Taxi Driver The Outlaw Josey Wales Rocky Network The Message All the President's Men The Omen The Tenant Star Wars: Episode IV - A New Hope Close Encounters of the Third Kind Annie Hall The Many Adventures of Winnie the Pooh Animal House The Deer Hunter Halloween Midnight Express Dawn of the Dead Watership Down Days of Heaven Drunken Master Alien Apocalypse Now The Warriors Stalker Life of Brian Kramer vs. Kramer Escape from Alcatraz Being There Manhattan The Muppet Movie The Blues Brothers The Shining Star Wars: Episode V - The Empire Strikes Back Airplane! The Elephant Man Raging Bull Ordinary People Kagemusha Raiders of the Lost Ark An American Werewolf in London Das Boot The Road Warrior Blade Runner The Thing E.T. the Extra-Terrestrial First Blood Star Trek II: The Wrath of Khan Gandhi Sophie's Choice The King of Comedy The Verdict Pink Floyd: The Wall Fanny and Alexander The Secret of NIMH Fitzcarraldo Scarface Star Wars: Episode VI - Return of the Jedi The Right Stuff A Christmas Story The Meaning of Life Zelig Ghostbusters The Terminator Once Upon a Time in America Indiana Jones and the Temple of Doom Amadeus This Is Spinal Tap Paris, Texas Nausicaä of the Valley of the Wind Blood Simple. The Killing Fields Stranger Than Paradise The Goonies Back to the Future The Breakfast Club The Color Purple Brazil Come and See Ran After Hours The Purple Rose of Cairo Stand by Me Ferris Bueller's Day Off Aliens Platoon The Fly Blue Velvet The Name of the Rose Castle in the Sky Down by Law Hannah and Her Sisters Predator The Princess Bride Full Metal Jacket Lethal Weapon The Untouchables RoboCop Empire of the Sun Evil Dead II Planes, Trains & Automobiles The Last Emperor Wings of Desire Withnail & I Au Revoir les Enfants Die Hard Rain Man Mississippi Burning Who Framed Roger Rabbit Grave of the Fireflies My Neighbor Totoro A Fish Called Wanda Cinema Paradiso Dangerous Liaisons Akira The Naked Gun: From the Files of Police Squad! The Big Blue Midnight Run The Last Temptation of Christ The Vanishing Dead Poets Society The Little Mermaid Batman Indiana Jones and the Last Crusade Back to the Future Part II Do the Right Thing When Harry Met Sally... The Abyss National Lampoon's Christmas Vacation Glory Kiki's Delivery Service My Left Foot Henry V Crimes and Misdemeanors The Killer Goodfellas The Hunt for Red October Misery The Godfather: Part III Edward Scissorhands Dances with Wolves Awakenings Miller's Crossing The Silence of the Lambs Terminator 2 Beauty and the Beast Boyz n the Hood Fried Green Tomatoes JFK The Fisher King Barton Fink Night on Earth Delicatessen The Double Life of Veronique Aladdin Unforgiven Malcolm X Reservoir Dogs My Cousin Vinny The Last of the Mohicans A Few Good Men Scent of a Woman Army of Darkness Glengarry Glen Ross Chaplin Porco Rosso The Player Hard Boiled The Muppet Christmas Carol Jurassic Park Schindler's List The Sandlot Dazed and Confused The Fugitive True Romance Tombstone What's Eating Gilbert Grape The Nightmare Before Christmas Groundhog Day Philadelphia Carlito's Way A Bronx Tale Falling Down Blood In, Blood Out The Piano In the Name of the Father The Remains of the Day Short Cuts Three Colors: Blue Naked Batman: Mask of the Phantasm Ninja Scroll The Shawshank Redemption Pulp Fiction The Lion King Forrest Gump Léon: The Professional Interview with the Vampire: The Vampire Chronicles Clerks The Crow Ed Wood Chungking Express Once Were Warriors Three Colors: Red Three Colors: White The Legend of Drunken Master Il Postino Everyone Has Their Own Style Se7en Braveheart Heat The Usual Suspects Toy Story Casino Twelve Monkeys Leaving Las Vegas Apollo 13 Before Sunrise Sense and Sensibility Die Hard with a Vengeance A Little Princess Ghost in the Shell La Haine Dead Man Whisper of the Heart The City of Lost Children Dilwale Dulhania Le Jayenge Underground Fargo Trainspotting Primal Fear Sleepers Sling Blade Hamlet Shine Breaking the Waves The Bandit Secrets & Lies Titanic Good Will Hunting The Game Boogie Nights The Fifth Element L.A. Confidential Life Is Beautiful Princess Mononoke As Good as It Gets Gattaca Donnie Brasco Lost Highway Perfect Blue Open Your Eyes Funny Games Children of Heaven The Sweet Hereafter The Big Lebowski Saving Private Ryan Fear and Loathing in Las Vegas American History X The Truman Show Mulan Lock, Stock and Two Smoking Barrels The Thin Red Line Dark City Rushmore Happiness Following Run Lola Run The Legend of 1900 The Red Violin The Celebration Black Cat, White Cat Le Dîner de Cons Central Station Fight Club The Green Mile The Matrix American Beauty The Sixth Sense Office Space Toy Story 2 Magnolia The Boondock Saints October Sky The Iron Giant Being John Malkovich The Insider Boys Don't Cry The Hurricane South Park: Bigger, Longer & Uncut The Straight Story All About My Mother Gladiator American Psycho Requiem for a Dream Memento Remember the Titans Snatch Almost Famous Cast Away O Brother, Where Art Thou? Crouching Tiger, Hidden Dragon Traffic Battle Royale Billy Elliot In the Mood for Love Amores Perros Dancer in the Dark You Can Count on Me Nine Queens Hera Pheri Vampire Hunter D: Bloodlust Harry Potter and the Sorcerer's Stone The Lord of the Rings: The Fellowship of the Ring Ocean's Eleven Training Day Donnie Darko Spirited Away Monsters, Inc. Shrek Mulholland Drive A Beautiful Mind Black Hawk Down Amélie Blow Moulin Rouge! The Others Y Tu Mamá También The Royal Tenenbaums Enemy at the Gates I Am Sam Lagaan: Once Upon a Time in India The Man Who Wasn't There Waking Life Hedwig and the Angry Inch Cowboy Bebop: The Movie The Experiment No Man's Land Dil Chahta Hai My Sassy Girl Vizontele The Lord of the Rings: The Two Towers Catch Me If You Can City of God Minority Report The Pianist The Bourne Identity Gangs of New York 28 Days Later... Road to Perdition Ice Age The Count of Monte Cristo 25th Hour Adaptation. Hero Infernal Affairs Whale Rider Sympathy for Mr. Vengeance Talk to Her Lilya 4-Ever In America Interstate 60: Episodes of the Road The Lord of the Rings: The Return of the King Finding Nemo Kill Bill: Vol. 1 Pirates of the Caribbean: The Curse of the Black Pearl Oldboy Love Actually Lost in Translation The Last Samurai Mystic River Big Fish Dogville Memories of Murder 21 Grams The Life of David Gale Good Bye Lenin! House of Sand and Fog The Station Agent The Return Spring, Summer, Fall, Winter... and Spring Love Me If You Dare The Triplets of Belleville Kal Ho Naa Ho Evil The Blind Swordsman: Zatoichi The Barbarian Invasions Munna Bhai M.B.B.S. The Incredibles Eternal Sunshine of the Spotless Mind The Notebook Harry Potter and the Prisoner of Azkaban Man on Fire Shaun of the Dead Million Dollar Baby Saw Collateral Howl's Moving Castle Kill Bill: Vol. 2 The Machinist Downfall Crash The Butterfly Effect The Bourne Supremacy Before Sunset Finding Neverland Kung Fu Hustle Hotel Rwanda Ray House of Flying Daggers Dead Man's Shoes A Very Long Engagement Mysterious Skin The Sea Inside The Motorcycle Diaries The Chorus Swades Veer & Zaara Head-On 3-Iron G.O.R.A. Tae Guk Gi: The Brotherhood of War Batman Begins Harry Potter and the Goblet of Fire Pride & Prejudice Sin City Serenity V for Vendetta Kiss Kiss Bang Bang Brokeback Mountain Star Wars: Episode III - Revenge of the Sith Walk the Line Cinderella Man Munich Lord of War Match Point Thank You for Smoking Lady Vengeance My Father and My Son The World's Fastest Indian A Bittersweet Life C.R.A.Z.Y. Black Adam's Apples The Departed The Prestige 300 Casino Royale Inside Man Children of Men Pan's Labyrinth Apocalypto The Lives of Others Little Miss Sunshine The Pursuit of Happyness The Illusionist Blood Diamond Letters from Iwo Jima Little Children The Fall Lucky Number Slevin This Is England United 93 Stranger Than Fiction The Last King of Scotland Black Book Rang De Basanti Paprika Death Note Fearless The Girl Who Leapt Through Time Volver After the Wedding Keep at It Munna Bhai No Country for Old Men Hot Fuzz Ratatouille Superbad Into the Wild Stardust There Will Be Blood Gone Baby Gone Zodiac Atonement American Gangster The Bourne Ultimatum 3:10 to Yuma Like Stars on Earth Eastern Promises Grindhouse The Man from Earth La Vie en Rose The Great Debaters 5 Centimeters Per Second Once The Kite Runner Elite Squad The Diving Bell and the Butterfly Control 4 Months, 3 Weeks and 2 Days Persepolis Chak de! India The Counterfeiters Boy A The Visitor Jab We Met The Edge of Heaven The Dark Knight Iron Man Gran Torino Taken The Curious Case of Benjamin Button In Bruges WALL-E Slumdog Millionaire Changeling The Hurt Locker The Reader Kung Fu Panda The Boy in the Striped Pajamas Let the Right One In Seven Pounds Ponyo Ip Man The Wrestler Milk Hunger A Wednesday The Chaser The Wave Departures Frost/Nixon Waltz with Bashir Watchmen Inglourious Basterds Avatar The Hangover Star Trek Harry Potter and the Half-Blood Prince Up Zombieland Sherlock Holmes Moon The Blind Side Coraline Mr. Nobody The Secret in Their Eyes 3 Idiots District 9 500 Days of Summer Fantastic Mr. Fox The Girl with the Dragon Tattoo Hachi: A Dog's Tale A Single Man Mary and Max Cell 211 A Prophet Mother The White Ribbon Sin Nombre About Elly The Secret of Kells The Breath Inception Shutter Island Harry Potter and the Deathly Hallows: Part 1 Tangled Despicable Me The Town Black Swan The Social Network Kick-Ass How to Train Your Dragon Toy Story 3 The King's Speech True Grit The Fighter Flipped Incendies 127 Hours Tucker and Dale vs Evil I Saw the Devil The Man from Nowhere Ip Man 2 The Secret World of Arrietty My Name Is Khan 13 Assassins In a Better World Elite Squad: The Enemy Within Confessions Udaan Harry Potter and the Deathly Hallows: Part 2 The Help The Girl with the Dragon Tattoo X-Men: First Class Drive The Intouchables Warrior Midnight in Paris The Raid: Redemption Moneyball Rise of the Planet of the Apes 50/50 A Separation The Skin I Live In The Artist The Flowers of War Headhunters Detachment Zindagi Na Milegi Dobara Once Upon a Time in Anatolia The Avengers The Dark Knight Rises Django Unchained The Hobbit: An Unexpected Journey Wreck-It Ralph Les Misérables Skyfall The Perks of Being a Wallflower Moonrise Kingdom The Impossible Silver Linings Playbook Argo The Hunt Life of Pi End of Watch The Body Gangs of Wasseypur Amour Wolf Children The Broken Circle Breakdown Barfi! Paan Singh Tomar OMG: Oh My God! Kahaani English Vinglish Vicky Donor The Wolf of Wall Street Her Prisoners Blue Is the Warmest Color The Hobbit: The Desolation of Smaug 12 Years a Slave Gravity About Time Dallas Buyers Club Star Trek: Into Darkness Rush Captain Phillips The Best Offer Before Midnight The Book Thief The Great Beauty Short Term 12 Nebraska Tangerines The Wind Rises Philomena The Tale of the Princess Kaguya The Lunchbox The Past Queen Special 26 Bhaag Milkha Bhaag Guardians of the Galaxy Interstellar Kingsman: The Secret Service Ex Machina Gone Girl Big Hero 6 The Grand Budapest Hotel Edge of Tomorrow Whiplash Captain America: The Winter Soldier Fury X-Men: Days of Future Past The Fault in Our Stars The Imitation Game Birdman or What We Do in the Shadows Nightcrawler The Lego Movie How to Train Your Dragon 2 Dawn of the Planet of the Apes The Theory of Everything Boyhood Wild Tales PK The Raid 2 Song of the Sea Mommy Pride Haider Winter Sleep Leviathan Mad Max: Fury Road Room The Martian Sicario The Hateful Eight The Revenant Bridge of Spies Spotlight Star Wars: The Force Awakens The Big Short Straight Outta Compton Inside Out Creed Me and Earl and the Dying Girl Beasts of No Nation Bajrangi Bhaijaan The Little Prince Victoria A Man Called Ove Drishyam Baahubali: The Beginning Mustang Baby Deadpool Moana Captain America: Civil War Arrival Hacksaw Ridge Zootopia La La Land Rogue One: A Star Wars Story Captain Fantastic Your Name. Hell or High Water The Invisible Guest Hidden Figures Dangal Manchester by the Sea The Handmaiden Lion Kubo and the Two Strings Hunt for the Wilderpeople Perfect Strangers Sing Street The Salesman I, Daniel Blake Airlift Pink The Greatest Showman Thor: Ragnarok Three Billboards Outside Ebbing, Missouri Blade Runner 2049 Guardians of the Galaxy Vol. 2 Coco Baby Driver Call Me by Your Name Dunkirk Get Out Logan Wonder Wind River Only the Brave Phantom Thread Paddington 2 The Florida Project The Big Sick Gifted Loving Vincent Baahubali 2: The Conclusion Avengers: Infinity War Deadpool 2 Mission: Impossible - Fallout Upgrade Ready Player One A Quiet Place Incredibles 2 Isle of Dogs Love, Simon Sanju ; proc iml; /* Compare expected distance between keys on a 7x6 vs 4x11 keyboard, assuming letters selected at random */ start DistMat(rows, cols); s = expandgrid(1:rows, 1:cols); return distance(s, "CityBlock"); finish; D = DistMat(7, 6); AvgDist_76 = mean(colvec(D)); print AvgDist_76[L="Avg Distance on 7x6 Grid"]; D = DistMat(4, 11); AvgDist_411 = mean(colvec(D)); print AvgDist_411[L="Avg Distance on 4x11 Grid"]; use Movies; read all var {"Title"}; close; MeanLen = mean(length(Title)); print MeanLen[L="Mean length of 1000 Titles"] ((AvgDist_76 - AvgDist_411)*MeanLen)[L="Expected Diff"]; /*********************************************/ /* return a matrix that contains the characters on the Netflix 'keyboard' interface */ start NetflixKeyboard(keys); keys = j(7,6,' '); keys[1:3] = 'S1':'S3'; keys[4:6] = 'BS1':'BS3'; keys[7:32] = 'A':'Z'; keys[33:41] = '1':'9'; keys[42] = '0'; finish; /* return a distance matrix for each key on the Netflix 'keyboard' interface */ start NetflixDistMat(keybd); s = expandgrid(1:nrow(keybd), 1:ncol(keybd)); return distance(s, "CityBlock"); finish; /* How many arrow keys are required to type a title by using a grid interface? The cursor starts at 'startPos' and the space key(s) are located at 'SpacePos' */ start RemoteDist(title, keys, D, startPos, SpacePos); t = upcase(title); Letters = substr(t, T(1:length(t)), 1); /* vector of characters in title */ dist = j(nrow(Letters), 1, .); s1 = startPos; /* cursor starts on this key position */ do i = 1 to nrow(Letters); /* for each letter in this movie's title */ L2 = Letters[i]; if L2 = ' ' then /* find position of closest space character */ s2 = D[s1, SpacePos][>:<]; /* index w/ min distance to a space */ else s2 = loc(keys=L2); /* position of non-space key */ /* if s2 was found, use it; else skip it (e.g., punctuation) */ if ncol(s2)>0 then do; /* the letter is in the table */ dist[i] = D[s1, s2]; /* find distance */ s1 = s2; /* update current location */ end; end; *print Letters dist; return sum(dist); finish; /* In the Netflix interface, the cursor starts on 'A' (position 7). Spaces are located in postions 1:3 */ start NetflixDist(title, keys, D); return RemoteDist(title, keys, D, 7, 1:3); finish; /* Modules are defined. Print keyboard and avg distance between keys, assuming haracters in title distributed uniformly at random. */ run NetflixKeyboard(NF); print NF[L="Netflix Interface for Remote Control"]; keys = rowvec(NF); distMat = NetflixDistMat(NF); *print distMat[r=keys c=keys]; EDistUnif = mean(colvec(distMat)); print EDistUnif; /* Test: How many arrow keys to specify The Wizard of Oz? */ OzDist = NetflixDist("The Wizard of Oz", keys, distMat); print OzDist[L="OzDist: Netflix"]; /* Compute empirical distances for 1000 popular movie titles */ use Movies; read all var {"Title"}; close; TotalDist = j(nrow(Title), 1, .); do i = 1 to nrow(Title); TotalDist[i] = NetflixDist(Title[i], keys, distMat); end; MeanDist = mean(TotalDist); MedianDist = median(TotalDist); print (meandist|| mediandist)[L="Netflix" c={"Mean" "Median"}]; title "Total Number of Key Presses for 1000 Movie Titles"; title2 "Netflix Keyboard"; /* call Histogram(TotalDist) other="refline 46 /axis=x;"; call scatter(length(Title), TotalDist) grid={x y}; */ NumChar = length(Title); RemoteDist = TotalDist; create NetflixDist var {"NumChar" "RemoteDist"}; append; close; /********************************************************************/ /* Perform an equivalent computation for the Amazon Video interface */ /********************************************************************/ /* return a matrix that contains the characters on the Amazon 'keyboard' interface */ start AmazonKeyboard(keys); keys = j(4,11,' '); keys[1:11] = {'Q' 'W' 'E' 'R' 'T' 'Y' 'U' 'I' 'O' 'P' 'BS'}; keys[12:22] = {'A' 'S' 'D' 'F' 'G' 'H' 'J' 'K' 'L' '123' 'CL1'}; keys[23:33] = {'Z' 'X' 'C' 'V' 'B' 'N' 'M' 'S1' 'S2' 'S3' 'CL2'}; keys[34:44] = ('1':'9') || {'0' 'ABC'}; /* actually, 'ABC' is in position (5,10), but (4,11) is same distance */ finish; /* return a distance matrix for each key on the Amazon 'keyboard' interface */ start AmazonDistMat(keybd); allkeys = rowvec(keybd); dist = j(ncol(allkeys), ncol(allkeys), .); keybd1 = keybd[1:3, ]; /* letters */ keybd2 = keybd[4, ]; /* numbers */ s = expandgrid(1:nrow(keybd1), 1:ncol(keybd1)); d1 = distance(s, "CityBlock"); /* distances between keys on main keyboard */ dist[1:33, 1:33] = d1; s = expandgrid(1:nrow(keybd2), 1:ncol(keybd2)); d2 = distance(s, "CityBlock"); /* distances between keys on secondary keyboard */ dist[34:44, 34:44] = d2; K123 = 21; /* position of key that transitions to secondary keyboard */ KABC = 11; /* position of key that transitions to primary keyboard */ distK123 = d1[ , K123]; /* distances to '123' key */ distKABC = d2[KABC, ]; /* distances to 'ABC' key */ d3 = repeat(distK123, 1, ncol(distKABC)) + /* add distances; +1 for transition */ repeat(distKABC, nrow(distK123), 1) + 1; dist[1:33, 34:44] = d3; /* distances between keys on primary and secondary keyboards */ dist[34:44, 1:33] = d3`; /* distances between keys on secondary and primary keyboards */ return dist; finish; /* In the Amazon interface, the cursor starts on 'Q' (position 1). Spaces are located in postions 30:32 */ start AmazonDist(title, keys, D); return RemoteDist(title, keys, D, 1, 30:32); finish; /* Modules are defined. Print keyboard and avg distance between keys, assuming haracters in title distributed uniformly at random. */ run AmazonKeyboard(AM); print AM[label="Amazon Search Grid for Remote"]; keys = rowvec(AM); distMat = AmazonDistMat(AM); *print distMat[r=keys c=keys]; EDistUnif = mean(colvec(distMat)); print EDistUnif; /* Test: How many arrow keys to specify The Wizard of Oz? */ OzDist = AmazonDist("The Wizard of Oz", keys, distMat); print OzDist[L="OzDist: Amazon"]; /* Compute empirical distances for 1000 popular movie titles */ use Movies; read all var {"Title"}; close; TotalDist = j(nrow(Title), 1, .); do i = 1 to nrow(Title); TotalDist[i] = AmazonDist(Title[i], keys, distMat); end; MeanDist = mean(TotalDist); MedianDist = median(TotalDist); print (meandist|| mediandist)[L="Amazon" c={"Mean" "Median"}]; /* title2 "Amazon Keyboard"; call Histogram(TotalDist) other="refline 56 /axis=x;"; */ NumChar = length(Title); RemoteDist = TotalDist; create AmazonDist var {"NumChar" "RemoteDist"}; append; close; QUIT; /* combine data sets: long form (stacked vertically) */ data AllLong; set NetflixDist(in=Net) AmazonDist; if Net then Keyboard = "NetFlix"; else Keyboard = "Amazon "; run; /* comparative histograms of distances for 1000 titles for each interface */ proc univariate data=AllLong; label RemoteDist = "Number of Keys Pressed"; class Keyboard; histogram RemoteDist / endpoints=(0 to 270 by 10) odstitle="Keys Pressed for 1,000 Movie Titles"; inset mean median / pos=NE; run; /* combine data sets: wide form (stack horiontally) */ data AllWide; label AmazonDist="Amazon Layout" NetflixDist="Netflix Layout"; merge Movies NetflixDist(rename=(RemoteDist=NetflixDist)) AmazonDist(rename=(RemoteDist=AmazonDist)); Diff = AmazonDist - NetflixDist; NetflixBetter = sign(Diff); run; /* for how many titles does the Netflix interface require fewer/more/same keypresses */ proc freq data=AllWide; tables NetflixBetter; run; /* paired t test shows significant difference between means */ proc ttest data=AllWide; paired AmazonDist*NetflixDist; ods exclude ConfLimits ProfilesPlot AgreementPlot QQPlot; run; /* add text for scatter plot */ data Text; xx=200; yy=50; text="Netflix interface/requires fewer keys/for these titles"; output; xx=70; yy=180; text="Amazon interface/requires fewer keys/for these titles"; output; run; data All2; set AllWide Text; run; ods graphics / width=480px height=480px; title "Two Interfaces to a TV Remote Control"; title2 "Number of Arrow Keys to Specify Each Title"; proc sgplot data=All2 noautolegend aspect=1; scatter x=AmazonDist y=NetflixDist; text x=xx y=yy text=text / backfill fillattrs=(color=white) textattrs=(size=10) SPLITCHAR="/" splitjustify=left SPLITPOLICY=SPLITALWAYS; lineparm x=0 y=0 slope=1 / clip; xaxis grid offsetmin=0.01; yaxis grid offsetmin=0.01; run; /* Print titles that require most/fewest keys */ proc sort data=AllWide; by descending AmazonDist; run; option ls=74; title "Titles That Require the Most Key Presses"; proc print data=AllWide(obs=10) noobs label; var Title NumChar NetflixDist AmazonDist Diff ; run; title "Titles That Require the Fewest Key Presses"; proc print data=AllWide; where NetflixDist<10 OR AmazonDist<10; var Title NumChar NetflixDist AmazonDist Diff ; run; title "Titles That Require the Same Number of Key Presses"; proc print data=AllWide; where NetflixDist=AmazonDist; var Title NumChar NetflixDist AmazonDist Diff ; run;