Friday, January 30, 2015

AirDroid to the Rescue

Last night I needed to send a slew of SMS messages, and tapping them out on the on-screen keyboard was just not an option I was excited about. I could have grabbed my bluetooth keyboard, or arranged for a Tasker AutoRemote solution, but all that seemed like more hassle then I wanted to bother with. So I busted out AirDroid.

If you're not familiar with AirDroid, it's one of those incredibly polished apps that you can't believe they give away for free. At least that's how I think about it.

Starting the AirDroid app on your cell phone doesn't appear to do much:

Notice, however, that it gives two web addresses: and It's the second one that's of special note. I type that into my web browser and I'm presented with what appears to be a computer desktop:

That 'desktop' is actually an interactive access to my phone. I can use it to transfer files, grab photos from the camera, look up contacts, access the clipboard, and yes, send/receive text messages. Actually, it does even more than that. The messaging application is pretty basic, but for hammering out the text messages I needed to send it was perfect.

You might be alarmed that I mentioned the URL to access my phone above. Thing is, that URL is on my local network. So unless you're on my WiFi network, you're not getting into my phone. Not only that, but before AirDroid starts in the browser you need to confirm that you wish to allow the connection.

This is an especially impressive configuration because the setup (appears to me) to be self contained. You install the app on your phone, and it servers as the server with which to launch your desktop experience. To use the buzzword of the day, in this scenario, you're skipping the Cloud. My messages, contacts, etc. never leave my local network. I find this more of an impressive programming feat than a required security feature, but it works as that too.

AirDroid also supports skipping this whole local network non-sense, and if you want, you can signup for an account which allows you to access your phone without first being on a specific local network.

Whether it's sending text messages, tweaking ring tones, or doing any activity that has you hunched over your phone, you should definitely check out AirDroid. If you're like me, you'll get lucky and be able to complete the same task using a full keyboard and screen.

Review: Char Bar

Well, any karma I earned for eating at a vegan restaurant last week was pretty much wiped out thanks to my trip to Char Bar last night. Char Bar is version 2.0 of Eli's Kosher Restaurant, and is a Kosher meat eater's paradise.

Eli's used to be the only full Kosher restaurant in DC, so while it wasn't the most beloved of restaurants, the food was always a treat for someone like myself.

As David and I learned last night, Char Bar is quite a number of steps up from the original. The ambiance alone is a huge improvement, trading what I recall as dim and cramped seating for a spacious and pleasant dining experience. And then there's the food. Gone are the classics like falafel and schwarma, and replaced are fancy burgers and $30+ entrees (glazed duck, anyone?). This might not be ideal for everyday eating, but for an every-once-in-a-while-special-treat, I'll take the fancier/pricier options.

Last night David and I split the Hickory Burger and a Steak Burger. They were both outstanding, and I left there so full I thought I might explode:

Seriously, I can't believe I ate the whole thing:

I've got to say, I'm really impressed. If you keep Kosher, and you haven't found your way to Char Bar, do so immediately. Heck, even if you don't keep Kosher, Char Bar is worth your time. Actually, that's probably the highest praise I can offer for any Kosher restaurant.

Thursday, January 29, 2015

That Time DC Tried To Be The Center of The World

Check out this map of Virginia from 1845:

And check out this note at the top of it:

That's right, the Prime Meridian of this map puts 0 degrees longitude right through Washington, DC. Fair enough, you might say, Virginia is right next to DC. Perhaps this was some sort of anomaly. Well, consider this map of Iowa created in 1845:

The top of the map reads "Longitude West From Greenwich", but check out the bottom of the map:

There it is again, "Longitude West from Washington."

These aren't just Cartographers Gone Wild, they're following the guidelines set forth by one Secretary of State Thomas Jefferson:

Jefferson wished for the United States to become scientifically as well as politically independent from Europe, so he wished for the new national capital itself to be a new "first meridian".

That's right, if Europe can have their own Prime Meridian, then why can't we have one? Many a politician may act as though Washington, DC is the center of the world, but Thomas Jefferson wanted to make it official. Heck, he did make it official.

But then came the Prime Meridian International Conference of 1884, and all those shenanigans came to an end. When the debate was all said and done, 22 out of the 25 countries agreed:

"That the Conference proposes to the Governments here represented the adoption of the meridian passing through the centre of the transit instrument at the Observatory of Greenwich as the initial meridian for longitude."

France and Brazil abstained, and San Domingo put their foot down and voted no. Not surprisingly, France, Brazil and Dan Domingo that voted yes to this provision:

Resolved, That the initial meridian should have a character of absolute neutrality. It should be chosen exclusively so as to secure to science and to international commerce all possible advantages, and especially should cut no great continent—neither Europe nor America.

In the end, Greenwich won out, and now anytime I have a time in UTC format, I need to bust out to make sense of it. If Jefferson's plan had worked, I'd be *in* UTC time.

You may be curious what brought all this on. Last night I ran to Meridian Hill Park, so named because it sits on the former Prime Meridian. Meridian Hill Park is a truly interesting place, with truly interesting statues. But when I arrived at 9pm last night, it was truly spooky. Here's a spooky tree:

I look forward to returning to the park in the daylight when I can find the state of a woman riding a horse in DC (there are 30+ equestrian statues in DC), among other gems.

DC is just full of surprises.

Update Just so happens David and I were a few blocks from another American Meridian related site. This one is found on the streets surrounding George Washington University, and it's similar to the line in Greenwich, though with a whole lot less fan fair. I've been in that GW neighborhood dozens of times and never ran across it:

Wednesday, January 28, 2015

A Teachable Twitter Moment

Somehow the good folks at arlnow interpreted this tweet:

as: APS to Students: Stop Being Mean to Us on Twitter. Let's ignore the obvious click bait for a second.

I think these crude student tweets do offer a Teachable Moment. However, I'd say it's not really about "technology polices" (whatever that means). To me, it's this: when you use Twitter (or Facebook, or MySpace or Snapchat or Whatever) you're speaking on the permanent record.

The snarky tweet that you're so proud of can be read months or even years later. Will the manager of the summer intern program, or the college admissions officer find that tweet clever, or will it flag you as someone they want nothing to do with? That's a lot to consider when you're dashing off a quick message, but that's life on the web. With great power comes great responsibility.

And the knee jerk reaction by parents, teachers, and others of denying access to Twitter and other publishing platforms is in many cases just as misguided. When that manager or admissions officer searches for you on the web (and you should assume they will), having no-results found is a missed opportunity.

It's like the oft repeated financial advice: it's important to carry a little debt. Doing so, and paying it off regularly, shows that you can be trusted to borrow money. Same goes for your online presence: it's valuable to show that you know how to behave online.

So APS Students, go ahead and tweet all you like. Just assume that what you say will follow you forever. No pressure there.

The Joy Of Wires

Last week I was working away on my latest Dell Laptop when I realized my internet connection was ridiculously slow. Not only was it slow, but it was dropping packets left and right.

I don't have a Speedtest from that particular day, but here's a snapshot from this morning:

3.11 Mb/s down is just not that impressive. The day I was having problems it was even slower.

It was slow enough that I actually called Verizon (we have Fios). And as happens every once in a while, I talked to an informed and helpful representative (after waiting on hold for 30 minutes, or so). Unfortunately, I knew from my own testing that the bottleneck was actually between myself and my router; not with the Internet itself. Both my Dells, though especially the new one, were having slow ping times to the router in the basement.

The Fios support guy had me install the Verizon In Home Agent specifically so that we could look at the signal quality between my laptop and the router. Sure enough, the quality was sub par.

Yesterday, I wrote a quick script to capture the WiFi signal quality, and check out this graph:

Online Graphing
Graph maker

The graph goes from sub 50% signal strength up to above 90%. Here's the cool part: I "made" this graph by simply picking up my laptop and carrying it down to my router, and then back up to my office. The peak performance was when the laptop was just a few feet from the router. It's painfully obvious: my wireless router is in the exact wrong place in our home.

Luckily, as our home was getting finished, I had our contractor install Ethernet ports in all the rooms. Even 10 years ago when I did this, the idea of needing a wired connection seemed a bit silly. But I did it anyway.

I figured the solution to my connectivity woes was simple: plug my new Dell into a wired port and see if that gives me better network performance. And then I ran into my next snag: the Dell Inspiron 7547 doesn't have a physical Ethernet port. D'oh. I hadn't really considered this when I bought the laptop, though even if I had noticed it lacked wired networked support, I'd probably ignored that fact. Who uses wires these days?

Amazon to the rescue. For $18.99 I Primed myself a USB Ethernet dongle. When it arrived I plugged it in, and the speed test results were glorious. Here's what they were this morning:

That's a blazing 57 Mb/s down and 63 Mb/s up. Whooo!

Who loves wires? I love wires!

I suppose I should ding my new Dell as having a less powerful WiFi receiver than other laptops. And it's annoying that there's no built in Ethernet jack. But all things considered, I'm just happy that I can leverage the massive download speeds Fios is offering. And to do that, I'm going to need to use actual physical cable.

Incidentally, I also ordered this Ethernet Switch from Amazon, so that both my work laptops could share the same Ethernet drop in my office. So far, it's working out very well.

Tuesday, January 27, 2015

A Bloody Good Neighbor: Dr. Charles Drew

For the last 10 years or so, as I've walked to and from shul, I've passed a couple of blocks from this historic marker:

It marks the former residence of Dr. Charles Drew.

Chances are very good that you're familiar with Dr. Drew's work. That is definitely the case if you've ever had surgery, gotten a blood transfusion or responded to the plea to Give Blood and Save a Life. That's because Dr. Drew was a pioneer in the Blood Bank process:

Much of Drew's research, however, focused on one of the most challenging medical problems of that time: how to "bank" blood so it would be available for transfusions as needed. Blood loses its integrity--and thus its utility--soon after it leaves the blood vessels: it starts to clot, and soon the cellular elements, especially the white blood cells, deteriorate, and levels of electrolytes change.
Medicine now takes blood banks for granted, but the first ones presented many technical and administrative challenges to Drew and Scudder and their colleagues: blood had to be collected with sterile equipment, into sterile containers, and treated with anticoagulant, then stored at a constant temperature, in refrigerators that were reliably efficient and protected from electrical outages. Each donation had to be typed, and tested for syphilis (one of several diseases that could be transmitted via transfusion.) Donors had to be recruited, scheduled, and screened for obvious health problems before "bleeding." Nursing and laboratory personnel had to be trained in collecting, handling, and testing the blood, and standard procedures set up, including forms to track every step of the donation process. Their experiment, which ran for seven months, was a success, and served as the basis for Drew's dissertation, "Banked Blood," for which he received his doctor of medical science degree in June 1940.

Drew's work then went beyond the Blood Bank and tackled the challenge of collecting and using just the Plasma in blood:

His key findings, complex procedures, and standards for collecting, processing and storing blood proved his expertise and led to an appointment to head the Blood for Britain Project (BFB), an effort to transport desperately needed blood and plasma to Great Britain, which was under attack by Germany.
To separate plasma from blood cells, the team used centrifuging (separation of blood components by density) and sedimentation (separation of particles from a liquid). The plasma was then pooled from a collection of eight bottles using an anti-contamination technique under strict air and ultraviolet lighting conditions, and samples were cultured for bacteria. An anti-bacterial called Merthiolate was added to the blood product and batches were tested weekly. Finally, each batch was transferred to a shipping container and diluted with sterile saline solution. A final sample for bacteria-testing was taken before the containers were sealed and packed. By early August, a trial shipment of plasma was sent to England and confirmed "entirely satisfactory."

The fact that this process worked at all is amazing. But when consider that he was dealing with 1940's tech, it's downright amazing.

Drew even invents the notion of a Blood Mobile. You can see one in action here:

More photos can be found here.

And just how hard core was Dr. Drew? Well, he named his child Bebe for Blood Bank. That takes a dedicated scientist and an incredibly understanding wife.

Oh, and there's one more wrinkle to this story. Dr. Drew was African American. He had to cope with massive amounts of institutional racism just to be a practicing physician. Not to mention the very blood banks he helped developed wouldn't allow him and other African Americans to contribute to. Yes, the Internet Meme writes itself:

If you have heard of Dr. Drew, chances are pretty good that you've heard the legend surrounding his death. Apparently this was repeated as truth in a MASH episode. Turns out, it's not true that he died as a result of not getting a blood transfusion at an all white hospital:

His tragic death generated an enduring legend that Drew, the man whose transfusion research had saved so many lives, ironically bled to death because he was refused treatment at an all-white hospital, or was even denied a transfusion. Although the legend has been debunked repeatedly--by Drew's companions, witnesses at the hospital, his family, and others--it has persisted. Why? Perhaps, as historian Spencie Love has noted in her analysis of the Drew legend, (One Blood: the Death and Resurrection of Charles R. Drew), the facts of Drew's premature death were bent and blended together with the stories of genuine victims of medical segregation, to convey an underlying message about the consequences of racial prejudice. While understandable, the legend hardly does justice to Drew, a man who achieved so much before he died, and who worked to undo racial discrimination by demanding excellence of himself and of his students, without ever embracing the role of victim.

What a remarkable soul.

Monday, January 26, 2015

Review: Native Foods Cafe

This last Saturday night Shira and I ventured out for first visit to Native Foods Cafe, specifically the restaurant in Falls Church. I was pretty much blown away by the menu, with absolutely no idea what I should try first.

In the end, I got a Super Italian Meatball Sub, Shira got a Kung Pao (I think) bowl, and we split the Japanese Sesame Crusted Chicken Bites.

Yum, yum and yum!

I think it's always a little risky ordering something I make myself. What if I like their "meatball sub" as much as I like the one I make at home? That sort of defeats the purpose of going out, no? Luckily, their version far surpassed anything I've made. That's impressive, considering I usually use real cheese and they used vegan cheese. I'm telling you, everything from the bun to the sauce was perfect.

And the chicken bites - man, those were great.

The overall atmosphere / experience reminded me very much of Noodles & Company. Which is actually a good thing, as I like their practical you-order-they-deliver-it setup. For Saturday night, I suppose it would have been nice to have had real table service. But I'll gladly take the casual atmosphere and a menu full of amazing choices; then a more formal experience and a couple of basic menu selections to pick from.

Apparently there's a DC location which we've never been to. The Falls Church location was just too convenient to pass up (what, with lots of available parking).

Interesting bonus: as we pulled out of the parking lot, Shira remarked that the Indian Restaurant next a few doors down was the very first place we'd eaten Indian food. Hard to believe there was a time when Indian Food was considered especially exotic.

I'm telling you, Native Foods Cafe is worth a try.

Review: Lysol Healthy Touch No-Touch Hand Soap System

I picked up a Lysol Automatic Soap Dispenser from BJ's as more or less an impulse buy. For less than $10.00, how could I go wrong? And I've got to say, it works. The motion sensor is accurate and while it's a big o'l hunk of plastic, using it does feel a little luxurious. Shira's not exactly in love with the type of soap it uses, but she's definitely pleased with it overall.

Given how successful this purchase was, I have a feeling I'm going to be seeing more versions of these automatic soap dispensers throughout our house.

And besides, with the dispenser, I'm able to take photos like this one:

Thursday, January 22, 2015

The Power of Legos

Last night, as I was finishing up a run I got to thinking about our last trip: what was the most useful item we brought?

Ignoring the standard stuff (cell phone, camera, bottle of water, etc.) I decided that props would have to go to this guy right here:

That would be a snack size Ziploc bag (6.5" x 3.25") filled with a random collection of Legos (actually, some pieces in the bag aren't even real Legos, but a cheap knockoff).

That tiny bag of Legos provided for hours of entertainment for the 5 1/2 year old traveling with us, be it in the car, at a restaurant or in the hotel room.

There's broadly two different ways to play with Legos: one, as an exercise in following instructions and two, as an exercise in creativity. (Of course, that's the tip of the iceberg: they also work as everything from prototyping material to photographic subjects.)

Growing up we'd try our hand at both approaches: first by diligently building the model described in the box, and then eventually tearing it down and adding the pieces to the countless Avon boxes worth of Legos in our home. From those Avon boxes, we could build our own massive armies of ships, vehicles and pretty much any other implement of war we wished. It was good times, and besides keeping us occupied no doubt contributed to my creative problem solving skills. As a kid I couldn't draw or paint, but I could build a star ship with the best of them.

It's good to see that this spirit of creativity lives on. I was delighted to observe that our little traveler was able to combine the Legos in ways I hadn't thought of, and was overjoyed to see him mixing and matching his creations with other toys available to him (like the track he built for his toy monorail).

If I had it to do over again, I'd be sure to bring a disposable cake pan which would have been the perfect lap desk while playing with the Legos in the car. We happened to have a sheet of cardboard which did the trick almost as well.

I suppose the true evidence that the Legos Work is that with them in hand, I didn't hear one request to "play a game on my cell phone."

Want to put together your own portable creativity kit? I'd suggest picking up a few of the Lego Polybag sets, like: this one, this one, this one and/or this one, and a package of random minifigs. Problem solved.

Wednesday, January 21, 2015

A Very Disney Weekend

I'm typing up this blog post in the glaring Florida sunshine as we head away from Disney World, the Most Magical Place on Earth. On Friday, we picked up our friend's 5 1/2 year old for a weekend full of Disney fun.

Saturday morning, he announced it was time to wake up. The fact that it was 5:50am didn't really matter. And so our first day of Disney began.

We took the bus to Magic Kingdom, and the three of us embraced our inner Mickey. Shira and our little traveler started off the day with a ride on Dumbo while I played line-holder for the Mine Train. As they finished Dumbo, they got right on the Mine Train and the day was off to a roaring start. They both humored me and we went on Ariel and Pooh "rides", two "slow moving rides" that were Ben approved.

Perhaps the most impressive feat of the Magic Kingdom is that the three of us walked 24,000+ steps--EACH (Actually, the little guy probably walked double that. Ouch). If my phone is to believed (which it isn't) that's over 11 miles. Yikes. No wonder our little guy absolutely crashed when we got to the hotel room. We tired him out so much that there was no 5am wake up call on Sunday.

For our second day of Disney adventure we hit Animal Kingdom, which is sort of a Disney version of a Zoo. I admit it, I enjoyed the "safari" ride because it gave me a chance to snap photos of animals without fences in the way. Actually, I enjoyed most of the animal exhibits. There's no denying it, when Disney does a zoo, they do it right.

Shira and the little guy enjoyed a roller coaster while I stood by and cheered them on. Other highlights of the park were the Boneyard (which was essentially a fancy playground) and a petting zoo. Shira thoroughly enjoyed the Lion King show which included both fun singing as well as impressive gymnastic routines. We left the park at 8pm when it closed down, walking a mere 21,000 steps.

Today was spent exploring our resort grounds and getting in some swimming at the outdoor (but thankfully heated) pool. We're leaving exhausted but happy (that last ice cream sundae didn't hurt, I'm sure).

In some ways, Disney is still Disney. The Jungle Cruise and Swiss Family Robinson House are old standbys I've been on a number of times now. And while we used the Fast Pass system, there's no escaping the lines and crowds (especially at Magic Kingdom). And why, after charging what they do for admission, do they have some attractions that require you to drop in a dollar to play? You really need one more dollar from me?

But the parks did have a few new tricks up their sleeve. The Monsters, Inc. Laugh Floor was downright technically impressive. What looks to be a canned animated movie quickly gave way to the fact that it's actual comedians with avatar bodies. It's slick stuff. And while Pirates of the Caribbean was closed, there's a new (to me) at-your-own-pace adventure you can take advantage of nearby. You pick up a treasure map and search the area for special symbols. As you hover your magic wristband over the symbol the area comes alive either revealing your next clue or a treasure. It was a perfect adventure for our 5 year old, with him getting a thrill as he'd bring the clue to life. And I found the Disney Dining Plan was mostly a good thing. They have quite a range of items you can get as snacks, which helped keep the in-park sticker shock to a minimum.

The best part of the visit though, was seeing Disney through the eyes of a 5 1/2 year old. Simply put, to him, everything in the park is real. That's not some guy in a Buzz Lightyear suit - that's actually Buzz. Yes, it was confusing that he was just in the ride he was on, but he must be taking a break now to greet people. And those cannon sounds on the Treasure Hunt weren't just theatrical smoke and a recording, they were live rounds being launched our way. It's just an amazing way to experience Disney.

Definite good times! Here's a smattering of photos:

View Photos

Tuesday, January 20, 2015

Keep the Magic Alive: Using a Disney MagicBand with your Smart Phone

We're back from a long weekend at Disney World (post and pictures coming soon!), and along with a pile of laundry and e-mail, I've got one of these:

That's a Disney MagicBand, which is your digital room key, park ticket, ride pass and wallet. They're given out to kids and adults alike, and I've got to say, they were a convenient platform.

But now what do I do with it? Sell it on eBay?

The bands are used just like an NFC tag, so while at the park I attempted to scan mine with my phone's NFC reader. No luck. The documentation that came with the bands suggested they were perhaps RFID technology and not NFC.

This morning I did some further poking around. A kind soul has posted a complete teardown of the band. Apparently, it includes both a short range and long range RFID chip.

Disney fully acknowledges the MagicBands contain a long range RFID transmitter, which is apparently how they managed to get a photo of Shira on the Everest Roller Coaster without her ever explicitly stating she was on the ride. Well done, if you ask me.

I wasn't ready to give up on using my MagicBand for something techy, so I turned to Google and asked about NFC. Turns out, the band does contain an NFC tag. I tried detecting the tag with Tasker this morning, and sure enough, it found it:

Perhaps in the park I didn't touch the band against the correct location on my Galaxy S5? The NFC sweet spot isn't particularly large. Regardless, the above check mark means that the band is absolutely usable outside of a Disney context.

Given that Tasker can read the band ID, there's no shortage of magic that could be attached to the band. Right now, when I scan mine it announces: Take me back to Disney World. But it shouldn't take much to make the band actually do something useful.

I doubt Disney cares that I can recycle their band by using it in another tech project with ease. But I for one am glad they did this, and am glad to give them credit for it. Well played Disney, well played.

Thursday, January 15, 2015

Urbex for the Beginner

Urbex (as in Urban Exploration) is one of those activities that fascinate me. It's sort of like Geocaching, but instead of searching for some hidden cache, you're off exploring some long forgotten piece of humanity. Oh yeah, and it's usually, but not always, illegal (what with trespassing laws and all).

But man, the photographic opportunities are huge!

While there are some well known urbex sites in DC (some I've even photographed), the general attitude of those who participate is one of secrecy. Publishing too many specifics about a location is the perfect way to get it shuttered and/or vandalized.

Want to go exploring? I found this short guide to be really helpful.

For now, I'm much more likely to explore publicly available sites than say, climbing into subway tunnels. But still, what an awesome way to see the invisible parts of a city.

Go forth and explore - just don't forget the camera!

Wednesday, January 14, 2015

3 Paper Hacks: Get Organized, Recyle and Reuse

Hack #1: I've already got a paper based system for organizing my day. But if I didn't have such a system, I'd absolutely be using The Emergent Task Planner. This 'system' is essentially a form you fill in daily that helps you get stuff done:

The Emergent Task Planner (ETP) is a paper-based daily planning sheet designed to keep you focused in the face of chaos. Start the day by declaring what you want to get done, and the ETP helps you stick to the plan by with task, time, and scheduling support.

Besides the cleverly designed form, I love the philosophy that suggests that shooting for 3 accomplishments a day is a big deal. Better to focus on getting three (or even one!) thing done, then to have a massive TODO list that you never make a dent in.

The whole system is open source which means you can buy ready made notebooks, or just download and print the form yourself.


Hack #2: Recycling old Topo Maps for use as DIY Waterproof Notebooks. The title of the post pretty much says it all. While obvious in hindsight, I'd never thought about re-purposing high quality maps that are just sitting on my bookshelf into something of value. The instructions provided are straightforward, so give it a try.

Hack #3: Turn a Tyvek Mailer into a mini-notepad. While pondering the above hack I realized I didn't have a Topo Map handy to experiment on. But, I did have half a Tyvek Mailer on my desk. I wondered if that would as a substitute. Tyvek is waterproof and super durable, so that would definitely make for an interesting notepad.

I looked around for a form I could use to shape the pages and noticed a key tag from a recent trip to the car dealer. That may seem like an absurd size for a notebook, but that's only because you're not thinking like a Japanese student. In Japan they sell blank word pads, which apparently students use to learn vocabulary.

I went to work with my x-acto knife and ended up with this guy right here:

OK, that's not going to win me any Etsy design contests. But, it should make for a super slim, super durable notepad. And adding more 'pages' just means spending another few minutes trimming the Tyvek envelop that's still sitting on my desk.

For another Tyvek Mailer user, check out the recent suggestion by Improvised Life.

Update: Oooh, my little Tyvek notepad pairs well with a Sharpie Mini. Well that's a nice bonus.

Tuesday, January 13, 2015

Instant Photos on the Very Cheap

The Raspberry Pi platform is so cool, yet I've never had a good use case to justify buying one. Until today. Check out PrintSnap, a very low-fi instant camera:

(Via: PictureCorrect)

The idea is to use a thermal printer rather than film. While the print quality is pretty horrendous, the prints are dirt cheap. I mean, fractions of a cent per print.

Problem is, you can't buy a PrintSnap. At least not yet.

Then along comes ProgrammingPraxis, with an essay about setting up a Raspberry Pi security camera. The setup essentially involves configuring standard Linux tools to capture images from a Pi and ship them off over e-mail.

Whoa, if a Raspberry Pi can trivially grab photos, then can it also print to a thermal printer? Apparently so. Here's a few tutorials that show this is done: Little Box of Geek, Raspberry Pi Thermal Printer One-Time-Pad, Internet of Things Printer for Raspberry Pi.

Looks like this is totally doable. Heck, the Little Box of Geek even gives a detailed parts list. OK looks like this is going on the project TODO list.

Oh, and one last thought: maybe I'm over-thinking this. What if I could just print my photos from my cell phone? It's pricey, but this thermal printer claims to do just that. And eBay has a number of Bluetooh Receipt Printers that look like they may do the job. Nahhh, what's the fun in that.

Update: and here's two more useful links: SparkFun Thermal Printer, An open source kit for exploring the possibilities of internet-of-things printing.

Monday, January 12, 2015

The Most Powerful Computer You'll Never Own

Inspired by the movie the Imitation Game, I just had build my own Turing Machine (I know, I should have built one of these! Some day). While folks have built actual physical machines, I took the programmer's way out and made mine strictly virtual.

A Turing Machine is the theortical device Alan Turing devised in his 1936 paper on computability. To this day, Computer Science students are made to do battle with this machine and the theories that stem from it.

While it's been years since I've done any CS homework that involved Turing Machines, I can't recall actually ever implementing one. What a shame.

The web is filled with such simulators including: here, here and here. These were invaluable for refreshing my memory as to how a Turing Machine operates.

Implementing a Turing Machine was oddly satisfying. One has to contend with the fact that a program handed to a Turing Machine may never complete. I dealt with this by allowing the user to execute the machine in terms of blocks of cycles. So you create the machine, run it for 100 cycles, and if you want, run it 100 more.

Here's the code to create a machine. The program is actually Alan Turing's first example:

(define r1 '(((b _) (c 0 >))
             ((c _) (e _ >))
             ((e _) (f 1 >))
             ((f _) (b _ >))))
(define tm1 (make-tm 'b '() '() r1))

The rules specified by r1 are in the format:

 (((current-state current-symbol) (new-state new-symbol new-direction))

Invoking make-tm creates the new Turing Machine. You provide as arguments the initial state, initial tape-contents, list of halting states and the transition rules.

Once you've got the machine (tm1, above), you can invoke it with an integer to say how many cycles of the machine should execute (e.g., (tm1 10)).

Scheme truly shined as a host language: I was trivially able to make the machine operate on arbitrary states and tape contents. Also sexpr's were ideal for defining the state transition rules.

All of this may seem fairly unimpressive until you ponder this thought:

However odd it may sound for so simple a machine, the Turing Machine is the most powerful computing model known to computer scientists. In this context, "powerful" refers only to what it is capable of doing, not to how fast or efficiently it does it. It has been proven that a TM is capable of performing any computation that a modern computer can, given enough time. Infact, it is technically MORE powerful than modern computers, since it has no storage limitations.

Here's the complete source code for my simulator.

Update: Programming Praxis tackled the Turing Machine almost 5 years ago. I've updated my code below with their example.

; A Turing Machine Impl

(define (range lower upper)
 (if (>= lower upper) '()
     (cons lower (range (+ 1 lower) upper)))) 

(define (show . words)
 (for-each display words))

(define tape-cell '#(_))
(define tape-padding '#(_ _ _ _ _))

(define (make-tape contents)
 (cons 0 (vector-append (list->vector contents) tape-padding)))

(define (tape-head t)
 (car t)) 
(define (tape-items t)
 (cdr t))
(define (tape-read t)
 (vector-ref (tape-items t) (tape-head t)))
(define (tape-write t x)
 (vector-set! (tape-items t) (tape-head t) x)
(define (tape-move t direction)
 (let ((index (+ (tape-head t)
                 (case direction
                  ((< L) -1)
                  ((> R) 1)
                  ((- N) 0)
                  (else (error "Unknown tape movement: " direction))))))
  (cond ((= index -1)
         (set-cdr! t (vector-append tape-cell (tape-items t)))
         (set! index 0))
        ((= index (vector-length (tape-items t)))
         (set-cdr! t (vector-append (tape-items t) tape-padding))))
  (set-car! t index)

(define (display-tape t)
 (for-each (lambda (i)
            (let ((v (vector-ref (tape-items t) i)))
              (cond ((= i (tape-head t))
                     (show "[" v "]"))
                    (else (show v)))
              (show " ")))
           (range 0 (vector-length (tape-items t)))))

(define (tm-find state tape rules)
 (let ((needle (list state (tape-read tape))))
  (let loop ((rules rules))
   (cond ((null? rules) #f)
         ((equal? needle (caar rules)) (cadar rules))
          (loop (cdr rules))))))) 
(define (make-tm initial-state initial-tape halting-states rules)
 (let ((state initial-state)
       (tape (make-tape initial-tape)))
 (lambda (cycles)
  (let loop ((cycle 0))
   (show state ": ")
   (display-tape tape)
   (cond ((= cycle cycles) #t)
         ((member state halting-states) state)
         ((tm-find state tape rules) =>
          (lambda (dest)
           (let* ((new-state (car dest))
                  (new-symbol (cadr dest))
                  (new-direction (caddr dest)))
             (set! state new-state)
             (tape-write tape new-symbol)
             (tape-move tape new-direction)
             (loop (+ 1 cycle)))))
          (else 'no-matching-rules))))))

; Binary Counting -
(define r0 '(((walk  0) (walk  0 >))
             ((walk  1) (walk  1 >))
             ((walk  _) (count _ <))
             ((count 0) (walk  1 >))
             ((count 1) (count 0 <))
             ((count _) (walk  1 >))))
(define tm0 (make-tm 'walk '(0) '() r0))

; Turing's First Example 
(define r1 '(((b _) (c 0 >))
             ((c _) (e _ >))
             ((e _) (f 1 >))
             ((f _) (b _ >))))
(define tm1 (make-tm 'b '() '() r1))

(define r2 '(((0 1) (0 1 R))
             ((0 +) (1 1 R))
             ((1 1) (1 1 R))
             ((1 _) (2 _ L))
             ((2 1) (H 1 N))))
(define tm2
 (make-tm 0
         '(1 1 1 + 1 1 1 1)

Review: The Imitation Game

Careful, there may be spoilers below.

Shira and I got wild and crazy on Saturday night: we saw a movie in an actual movie theater! Man, I love those 25 minutes of previews! Anyway, the movie we saw was The Imitation Game, which is the story of Alan Turing.

Being a Computer Science Major, I'm already somewhat familiar with Mr Turing's work. He's sort of a Charles Darwin of Computer Science. To appreciate this you have to appreciate that Computer Science isn't really about Computers or Science. It's about the study of computation, and problem solving in general. Sure, we have to use these pesky physical machines but that's an implementation detail.

Alan Turing made great headway into understanding what's computable, and naturally to do this, he created his own computer and method of programming it. On the surface that may not be particularly impressive, but consider that he did this in 1936 or so. A decade before anyone even saw a computer, and years before computer programming would be a true pursuit, Alan Turing had already devised the most powerful computation machine on the planet, and proved that all general purpose computers were equivalent to his contraption.

So before I walked into the theater I had mad respect for the man.

For the next 2 hours I was fully entertained by the movie. As the previews suggest, the movie focuses on Turing's involvement with the effort to break Germany's WWII encryption technology. I had known of Turing's involvement in this effort, but the movie truly brought it to life. I suppose it's a special kind of challenge to tell a story where the outcome is known (I'm looking at you, Titanic), and the creators of the Imitation Game pulled it off well. So yes, the movie was entertaining and gave me a fresh perspective into Turing's life.

The first order of business after leaving the theater was to Google Imitation Game: differences from real life. It was obvious that they injected a dose of Hollywood into the movie, but how much of it was fake? Slate, among others, answers that question, and no surprise the results aren't pretty. Many of the moments I enjoyed in the film just plain never happened.

What do I think about this? I'm not sure. It's easy to kvetch, and say that they should have been more true to the story. But, at the end of the day, if the goal was to show just how amazing Turing was, perhaps they succeeded?

In end, I think the spirit of the film is in the right place. So go, watch it and enjoy. Just do your homework after the fact so you can separate fact from fiction.

Friday, January 09, 2015

Hack of the Day: Folding a Napkin into a Basket

Mark my words, one day you're going to thank me for this. Here's your hack of the day: fold a napkin into a basket. Of course I love this hack because I love all things Furoshiki and Furoshiki-like.

This hack is brought to you by Grant Thompson - King of Random. His YouTube channel is filled with all sorts of goodies. Go check it out. Or better yet, don't, as I'll probably be posting more of his videos here.

So here it is, how to fold a napkin into a basket:

View Video

Dude. Got another Dell. So far, Loving it.

It was time to retire my ASUS laptop, and as has become my tradition these last few years, I hit the local Best Buy to see what I could replace it with. I'm not much of a hardware guy, so I went in with basic requirements: i7 processor, at least 8 gig of RAM, touch screen and a big 'ol hard drive. I really wanted a touch pad with physical buttons. Oh yeah, I'd like a 15 inch screen or smaller. For all the traveling we do, it's still not enough to warrant an ultralight machine. Better to save a few bucks and not buy super skinny (which would spend nearly 100% of the time sitting on my desk).

All the usual players had laptops that fit my basic specs. I suppose if there was anything new to check out it was the plethora of 2 in 1 machines. Most of which are laptops that allow their screen to fold all the way back to create a crude tablet. While admittedly sexy, I don't lounge with my work laptop, so I can't really justify buying one of these bad boys. It's plain vanilla for me, as that's what I need on a day-to-day basis.

Another option was to buy a laptop with a Solid State Hard drive. But what the heck am I going to do with a 256 Gig drive? How do people function with that little disk space, when 1 Terabyte is basically standard?

In the end I picked up yet another Dell. This one is a Insprion 15 7547 (I think it's this one at BestBuy).

I think this is the first time in my life I've bought a new laptop and technology is essentially the same as the last one I bought. It's the same processor, hard drive, RAM and touch screen. Best Buy was offering a few laptops with with 12 Gig of RAM, which was awfully tempting. But in the end, I was won over by what appeared to be Dell's solid build quality.

And after a week of using this bad boy, I can say that Dell has delivered. The keyboard is between adequate and good. And while I'm unhappy that I couldn't get a touch pad with physical buttons (what the heck!), I've found that Dell's touch pad is working well enough. In many respects the laptop is as plain as could be, but for my purposes, that's exactly what I needed.

I continue to be amazed at how quickly I go from a blank system to functioning work device. Here's the process I went through to get up and running:

  1. Installed Chrome. Buh-by IE.
  2. Installed cygwin, and rather than messing around with package selection, I used all defaults and added subversion.
  3. Used subversion to check out a cygwin setup script I maintain. This cript installs all the packages I require
  4. Installed emacs. I've found this package to be an ideal one to install on Windows
  5. Installed Firefox
  6. Created my 5 Firefox profiles
  7. For each Firefox profile I customized the theme (this makes telling the profile apart much easier) and installed the Lazrus Form Recovery plugin. This makes auto-filling of any and all forms a breeze. It's a must have.
  8. On my Dev and Dev Jr. Firefox profiles I installed Firebug, Colorzilla, Web Developer and DNS Flusher.
  9. Installed Picasa
  10. Installed Gimp

And that was it. I was now able to develop, run my business and blog--my basic laptop activities. At some point I'll need to migrate files over from my ASUS machine, but I'm not in a huge hurry to do this.

This latest setup has really made me appreciate how much of my work is in version control. In fact, the only thing on my machine besides code seems to be photos. I'm thinking maybe I'll setup all my photo to sync via Google Drive and perhaps not bother with Carbonite? Yeah, probably not a good idea.

Anyway, the Dell Inpsiron 15 is a solid machine. It won't impress your hardware friends. But it just works.

Thursday, January 08, 2015

It Snowed. You Kvetched. You Got Your Apology. What's Next?

It's been a rough couple of days to be a Northern Virginia School Administrator (or, so I would guess). On Tuesday all hell broke loose when Fairfax and Arlington (among others) didn't close their schools. Both yesterday and today Fairfax and Arlington announced delays due to cold. And today, Fairfax turned their 2 hour delay into a full out cancellation. Tuesday's fiasco was large enough that it got Buzzfeed coverage.

The last few days have mostly been spent with various parties demanding and delivering apologies. It's not just the schools that are in on this game, meterologists and government workers chimed in, too.

While the tone of today's comments are generally positive towards Fairfax's choice to cancel school, it's still being couched in terms of whether or not the decision was effective.

I think something's missing from all this back and forth. It's something Arlington County, the Federal Government, your sketchy brother-in-law and your Scout Master have all been trying to tell you: unexpected stuff is going to happen, and when it does, it's up to *you* to be prepared to handle it.

Look, I love my government services. Public school buses that arrive on time; public roads treated for ice and cleared of snow; police ready to help a stranded motorist; sane instructions from schools and work officials. These are all good things. And most of the time, these services are in place. *But*, Tuesday's snow is a good reminder that it doesn't take much for the system to get shook up, mainly a few inches of snow falling on roads not ready for it, during rush hour. That's all it took and the city was in gridlock.

So take to Facebook and Twitter and vent. It's frustrating. And annoying. And by all means, push school administrators to do a better job (perhaps make the process more transparent? give bus operators a way to alert parents that the bus is going to be late? etc). But you should also use this opportunity to review your plan and prep.

Does your child know what to do if he's standing out in the cold waiting for a bus that doesn't come? Where should he go if you've already headed off to work? What happens when a 2 hour delay turns into a full blown snow day? Are you ready for a 4 hour commute in your car, or spending the night on the side of a highway? Probably not, and that's OK. But the time to take action is now. Look at these last few days and see if there's anything you could do to be ready for the next time the system goes off the rails. A little planning, a few strategic purchases, and you'll be in much better shape.

Looking for a place to start? has all the basics you'll need. Heck, they've got a commuter emergency plan, something I didn't even know existed. Luckily, my commuter plan consists of getting from my bed to the bathroom to my computer. Even on snow days, traffic tends to be light.

From The Cell Phone

Every few days I copy all the images off my cell phone and archive them on my computer. Here's a few photos that I thought were worth sharing, but weren't quite worthy of their own blog post. Enjoy.

Caption Me: FroYo Edition

(Context: last night we walked into Menchies and found the place apparently empty. The staff was in the back, doing their thing. With the frigid temps outside, an empty FroYo shop seemed more than reasonable)

Wednesday, January 07, 2015

A Little Forth, A Little Evolution

With a handful of Forth examples implemented, I wanted to try my hand at a slightly beefier challenge. So I busted out the Dawkins' Weasel example, and went to work.

Recall that Dawkins' Weasel is a programming exercise that demonstrates a core concept of evolution; mainly that random chance can lead to a non-random seeming result. The exercise shows how you can go from gibberish text to a meaningful statement via random mutation.

From a programming perspective, the challenge requires little more than basic array handling and random number generation. Luckily, Gforth provides both of these.

While I'm still wrapping my head around Forth, I was pleased to see that my final 'word' was deliciously simple:

: bang! ( -- )
  tick ..tick
  keep-ticking? while
 repeat ; 

It boggles my mind how Forth effectively doesn't have, nor need, a string (or even array) type. Simply storing characters in a raw block of memory works surprisingly well. I haven't done anything like this since I working with C pointers, and that was considered risky business. But in Forth, it's just business as usual.

I also found that my initial style of creating new instances of strings and workspaces1 for every generation caused me to run out of memory (technically I was using alot. and I hit a stack overflow). I ended up rewriting the program to overwrite memory. While this triggers all my functional programming alarm bells, it does result in a program that uses very little memory. I suppose I could have found a middle ground and used immutable structures with either garbage collection or explicitly freeing memory, that seemed like more hassle than it was worth.

From a performance perspective, the program is blazingly fast. My scheme implementation took minutes to run on my cell phone, whereas the Forth implementation below runs nearly instantly on the same device. I'm printing out the generation as they tick by, so most of the time is probably spent refreshing the screen. Here's what it looks like:

Without a doubt, the Scheme program is slow because of the way I coded it, not because Gambit Scheme is some how fundamentally slow.

This all has me wondering: what's the practical implication of having a highly efficient, yet esoteric, programming option on Android? I can't imagine ever implementing production code using Forth on Android, but maybe I should be. For the right app, it just make work.

Finally here's two Gforth app tips: (1) the up and down arrows will take you backwards and forwards in the history, and (2) there's tab-completion on words! Try it to see how well it works.

1A workspace is defined as a collection of strings that start from the same source, but are mutated. Every tick creates a new workspace, mutates it, and then selects the best scoring entry.

require random.fs

: 3dup ( x y z -- x y z x y z )
 2 pick 2 pick 2 pick ;
: between? { x lower upper -- bool }
 x lower >= and
 x upper <=  ;

: rand-between { lower upper -- n }
 upper lower -
 random lower + ;

: rand-char ( -- c )
 0 27 rand-between
 dup 26 = IF
  drop bl
  [char] A + 
 endif ;
: rand-fill { addr length -- }
 length 0
  rand-char addr i + c!
 loop  ;
: rand-string { length -- addr length }
 here length chars allot
 length rand-fill
 length ;

: rand-bool { percent-true -- n }
 100 random
 0 percent-true between? ;

: clone-string { addr length -- addr }
 here length chars allot { new-addr }
 addr new-addr length cmove
 new-addr ;

: overwrite-string ( from to length -- to )
 cmove ;

\ -------------------------------------

here GOAL-LENGTH chars allot



: make-attempt ( -- addr )
 GOAL-LENGTH rand-string drop ;
: clone-attempt ( addr -- new-addr )
 GOAL-LENGTH clone-string ;

: overwrite-attempt ( from to -- )
 GOAL-LENGTH overwrite-string ;
: mutate? ( -- yes-or-no )
 MUTATE-PERCENT rand-bool ;

: mutate-char ( addr -- )
 mutate? IF
  rand-char swap c!
 endif ;
: mutate-attempt { addr -- }
   addr i + mutate-char
 loop ;
: spawn-attempt ( addr -- new-addr )
 clone-attempt dup mutate-attempt ;

: install-attempt { from to -- }
 from to overwrite-attempt
 to mutate-attempt ;
: score-attempt-char { addr index -- score }
 addr index + c@
 GOAL-STRING index + c@
 = if 1 else 0 endif ;

: score-attempt { addr -- score }
 0 GOAL-LENGTH 0 u+do
  addr i score-attempt-char +
 loop ;  

: attempt-winner { attempt1 attempt2 -- winner }
 attempt1 score-attempt
 attempt2 score-attempt
 > if attempt1 else attempt2 endif ;

: .attempt ( addr -- )
 dup score-attempt . ." : "


: workspace-range ( ws-addr )
 dup WORKSPACE-SIZE cells + swap ;

: fill-workspace { ws-addr attempt-addr -- }
 ws-addr workspace-range u+do
  attempt-addr spawn-attempt i ! 
 cell +loop ;

: install-workspace { workspace attempt -- }
 workspace workspace-range u+do
  attempt i @ install-attempt
 cell +loop ;

: make-workspace { attempt -- }
 here WORKSPACE-SIZE cells allot
 dup attempt fill-workspace ;

: workspace-attempt ( ws-addr index -- attempt-addr )
  cells + @ ;
: workspace-winner { ws-addr -- attemp-addr }
 ws-addr 0 workspace-attempt
   ws-addr i workspace-attempt attempt-winner
  loop ;

: .workspace ( ws-addr -- )
 cr workspace-range u+do
  i @ .attempt cr
 cell +loop ;
: make-tick ( -- workspace generation attempt )
 dup make-workspace
 swap 0 swap  ;
: tick { workspace generation attempt -- workspace gen+1 attempt }
 generation 1+
 workspace attempt install-workspace
 workspace workspace-winner ;
: .tick ( workspace gen attempt )
 swap ." G:" . .attempt cr drop ;

: ..tick ( workspace gen attempt -- workspace gen attempt )
 3dup .tick ;

: keep-ticking? ( workspace gen attempt -- workspace gen attempt )
 dup score-attempt
: bang! ( -- )
  tick ..tick
  keep-ticking? while
 repeat ;  

Tuesday, January 06, 2015

Arlington's First Snow Fall of 2015 in Two Photos

This picture isn't scary:

That's the snow from our first snowfall on our front yard. It's cute how it almost, but doesn't completely cover the grass.

And this pictures is scary. I grabbed this screenshot at around 8:09am.

With the exception of a couple of streets within DC, every monitored roadway is red. Yikes.

If I ever wondered how a couple of inches of snow could paralyze one of the most powerful cities in the world, there you go.

Stay safe, use good judgement and enjoy the snow!

Monday, January 05, 2015

6 Coding Exercises to Reshape Your Programming Brain

The ProgramingPraxis Christmas / New Year's Exercise couldn't have come at a better time. Given my latest Forth on Android kick, it served as the perfect refresher course for this language I love in theory, yet can't code in practice.

The challenge was to reproduce 6 'ancient' algorithms, which range from implementing basic multiplication to calculating prime numbers.

The exercises were ideal because they forced me to deal with a number of core language constructs, such as recursion vs. iteration, floating point math, working with arrays and dealing with name clashes. They also got me thinking about bigger topics like code reuse, modularization and debugging. None of this is Forth specific, which means that this set of algorithms would be ideal for learning any new language.

I solved the exercise over a number of short coding sessions. What started as an agonizing struggle to implement basic multiplication (oh the stack makes my brain hurt!) finished with a Sieve of Eratosthenes implementation that begins to show a little beauty and elegance (at least in my head, it does). Mind you, any seasoned Forth programmer would look at my code below and shake his or her head. But for me, I was excited to see some of the nuances of Forth work for me (oh yeah, functions don't have to 'return' a single value!) rather than just serve as stumbling blocks.

Whether it's forth, haskell, C++ or any other language; this challenge really is ideal for busting you out of your comfort zone. Make sure you implement all 6, though. Had I given up after the first couple, I would have never got that Whoa! so that's what Forth programmers see when they see the world; remarkable!, feeling. And trust me, that feeling is awesome.

Here's the code. Try not to laugh too hard.

\ -----------------------------------------------------

: odd? ( n -- b )
 1 and 0<> ;
: even? ( n -- b )
 odd? 0= ;

: odd-value ( w1 -- w2 )
 dup even? if
  drop 0
 endif ;

: 3rd ( w1 w2 w3 - w1 w2 w3 w1 )
 2 pick ;

: pstep { lhs rhs sum -- new-lhs new-rhs sum }
  lhs 2 /
  rhs 2 * 
  lhs 2 / odd? if
    rhs 2 * sum +
  endif ;

: pinit { lhs rhs -- sum }
 lhs rhs
 lhs odd? if
 endif ;

: product { lhs rhs -- prod }
 lhs rhs pinit
  3rd 1 > while 
 2nip ;

: .mul { lhs rhs -- prod1 prod2 }
 lhs rhs product
 lhs rhs *
 .s clearstack ;
\ -----------------------------------------------------
0.00000001e0 fconstant fsqrt-epsilon

: fwithin? { F: x F: y F: error }
 x y f- fabs
 error f< ;

: fsqrt-needs-refining? { F: x F: n F: x' -- x n x' continue? }
 x' n x'
 x x' fsqrt-epsilon fwithin? IF
 endif ;

: fsqrt-step { F: n F: x -- n x' }
 x n x f/ f+ 2e0 f/ ;

: fsqrt { F: n -- x }
 n 1e0 ftuck
  fsqrt-needs-refining? while
 fnip fnip ; 
\ -----------------------------------------------------

: ^2 ( n1 -- n2 )
 dup * ;

: *3 ( n1 n2 n3 -- n4 )
 * * ;
: triple { m n -- a b c }
 m ^2  n ^2  -
 2 m n *3
 m ^2 n ^2 + ; 
\ -----------------------------------------------------

: gcd-step { m n -- m' n' }
 n 0= if
  m 0
  n m n mod
 endif ;
: gcd ( m n -- d )
  dup 0<> while
 drop ;

\ -----------------------------------------------------

: fpi-init ( -- outer inner )
 3e0 3e0 fsqrt f*
 fdup 2e0 f/ ;
: finv ( x -- 1/x )
 1e0 fswap f/ ;
: fpi-step { F: outer F: inner -- outer' inner' }
 2e0 outer finv inner finv f+ f/
 fdup inner f* fsqrt ;

: fpi { n -- approx }
 n 1 u+do
 loop fdrop ;

\ -----------------------------------------------------

: siv-addr ( s index -- addr )
 1 - cells + ;

: siv-upper ( s -- n )
 @ ;
: siv! ( value s index -- )
 siv-addr ! ;
: siv@ ( s index -- value )
 siv-addr @ ; 
: siv-init { s upper -- s }
 upper s !
 upper 1 + 2 u+do
  true s i siv!
 loop s ;

: siv-range { s start-index -- to from }
 s siv-upper 1 +
 start-index ;
: siv.s { s -- }
 s 2 siv-range u+do
  cr i . ." :" s i siv@ .
 loop cr ;

: new-siv { upper -- s }
 here upper cells allot
 upper siv-init ;

: siv-mark { s index -- }
 true s index siv!
 s index 2 * siv-range u+do
  false s i siv!
 index +loop ;
: siv-primes { s -- s }
 s 2 siv-range u+do
  s i siv@ if
   s i siv-mark
 loop s ;

: prime? ( n -- b )
 new-siv siv-primes
 swap siv@ ;
: primes { lower upper -- p1 p2 ... }
 upper new-siv siv-primes { s }
 upper 1+  lower u+do
  s i siv@ if
 loop ; 

Friday, January 02, 2015

Arlington Quiz: Name That Chunk of Rock

So what are those photos of?

The answer is here.

This post is brought to you by Field Tripper, an Android app that alerts you of interesting sites nearby. Like historical chunks of rock.

Thursday, January 01, 2015

New Year's Day Hike: Leesylvania State Park

If there's a better way to start a new year than a hike on January 1st, I haven't found it. We kept the tradition alive by hitting Leesylvania State Park with my Brother and Sister-in-Law.

I admit it, I didn't have high expectations for Leesylvania. On the pros side, it was a Virginia State Park, and chunk of green space that we had never explored. On the cons side, it didn't look especially large and I never really heard anyone recommend it.

Well, now I'm here to recommend it. The park was awesome. It had everything I could ask for: beautifully manicured trails, a beach to explore, historic sites (oooh, a grave yard!), geocaching, fishing, birding and all around amazing views. Yes, it's true, the park isn't huge. We did most of the in-park trails and that was about 5 miles of hiking. Though there is a section of the Potomac Heritage Trail that extends beyond the park which we didn't do.

The park, especially in the summer, would be idea to visit with kids.  Next to Leesylvania is Featherstone National Wildlife Refuge which is only accessible by boat. How cool is that?  That's going on my outdoor TODO list.

Oh, and Maryn noticed a couple of Munzee barcodes dangling from trees. So before you go out, you may want to install that app and play along. 

Whoa, I almost forgot the most important amenity of the park. It's located just a couple of miles from a Wegmans.  That meant a hot cup of soup and a fun shopping trip (well, fun for Shira) after freezing our tush's off.

All in all, an amazing park and an amazing day. What a way to kick of 2015!

View Photos