Day 47: Python Virtualenvs

If you’re not a Python programmer, you probably won’t find much in this post. Sorry.

If you are a Python programmer, then you probably know about virtualenvs, or virtual environments. They allow you to create several different Python environments to work in: each can have it’s own version of Python, as well as its own installed packages. This means I can work on a project that has particular requirements, and then switch to a project with completely different requirements, and the two won’t affect each other.

A while ago I used to use vitualenvwrapper, which made working with virtualenvs a lot easier. But as I switched to Python 3 over the past few years, I started to have some issues where it didn’t work correctly (sorry, I no longer recall precisely what those issues were). I’m sure a lot had to do with the addition of the venv module into Python 3, which allowed you to create a virtualenv by running python -m venv /path/to/virtualenv.

For a while I ran all the commands manually, but I have the quality that makes for good programmers: I’m lazy. A lazy person doesn’t want to do any more work than they have to, so if I can automate something to save time over the long run, I will. And here’s what I came up with:

export VENV_HOME=$HOME/venvs

function workon { 
    if [ -z $1 ]
    then
        ls -1 $VENV_HOME
    else
        source $VENV_HOME/$1/bin/activate
    fi
}

function mkvenv {
    python3 -m venv $VENV_HOME/$1
    workon $1
    pip install -U pip setuptools wheel
    pip install ipython pytest-pudb requests
}

function rmvenv {
    command -v deactivate
    rm -rf $VENV_HOME/$1
}

_venvdirs()
{
    local cur="$2"
    COMPREPLY=( $(cd $HOME/venvs && compgen -d -- "${cur}" ) );
}
complete -F _venvdirs workon rmvenv 
Code language: Bash (bash)

These lines should be added to your .bashrc in Linux, or your .bash_profile for Macs. I haven’t tried them with zsh yet, so no guarantees there. Let’s go over what these lines do.

Line #1 defines the directory where the virtualenvs will be stored. You can store them anywhere; it doesn’t make any difference.

Lines #3–10 define the workon function, which activates the specified virtualenv, or lists all virtualenvs if none is specified. Lines 12–17 define the mkvenv function, which creates a new venv, and lines 19–22 define rmvenv, which deletes virtualenvs when you no longer need them.

I’d like to point out 2 lines in mkvenv that you can customize. Line #15 updates the installed versions of pip, setuptools, and wheel. If for some reason you don’t want the latest versions of these, edit or remove that line.

Line #16 is more interesting: nearly every virtualenv I create needs these packages installed. Rather than install them one-by-one, I add them when I create the virtualenv. If you have different packages you always want available, edit this line.

Finally, lines #24–29 are of utmost importance to someone lazy like myself: they provide auto-completion for the other commands. I had to learn about bash completion to get that working, but it turned out to be much easier than I had imagined.

Here is a gif showing it in action:

Try it out! Let me know if you find this useful, or if you have suggestions for improvement.

Day 46: The First Emergence

Today was very busy, but doing lot a lot of different things rather than one main task. So it’s the early evening and I’m finally sitting down to write.

The day started off early: I had just put water on for our morning coffee, and while it was heating I checked out the caterpillar enclosures. I saw a lot of fluttering in one, and sure enough, there was a male butterfly trying to find its way out.

First butterfly of the brood

When the butterflies emerge, they typically hang out for a couple of hours until their wings are fully expanded and dry before they try to fly away. This guy must have emerged a few hours earlier, because he was raring to go. I took the above picture as he was crawling up the side of the enclosure. Once he reached the top, off he flew!

This was the first adult butterfly that came from this large crop of eggs that I found a few weeks ago:

29 swallowtail eggs!

The enclosures have been filling up with pupas from that brood. Here are a few of them:

Lots of pupas!

You might recognize the contraption made of sticks from an earlier post; there are now 7 pupas attached to it! the five unattached pupas are either caterpillars that attached to a sprig of parsley, which will dry up in the enclosure. Notice that the one on the right still has a bit of parsley stalk attached to it. Other caterpillars sometimes give up trying to find a place to attach themselves, and just curl up on the ground. I’ve had that happen before, and they result in normal butterflies, so I’m feeling positive that these will too.

There are only a few caterpillars left who are still munching away and getting bigger. The rest have pupated, so in the coming days I’m sure I’ll find a lot more butterflies emerging from those pupas. I just hope that they have the decency to wait until I’ve had my coffee before doing so!

Day 45: Composing Music and Code

I am not a musician. Yeah, I was a vocalist in a couple of bands in high school and college, but all I really did is copy the original song. The notion of coming up with a new approach to a song was way beyond my imagination.

I am amazed by people who can write their own original songs. How can you create a melody from… nothing? It really is beyond my ability to comprehend. Lyrics seem straightforward enough, but the music?

A few years ago at a conference I was hanging around in the evening with some friends, several of whom were musicians that had brought their guitars. One of them played a song, and I asked him where the song was from. He replied that it was one of his own. “Wait: you wrote that yourself?” That surprised the hell out of me!

Now that my curiosity was piqued, I couldn’t help but ask him how he does it. He replied that sometimes he has some little bits of music in his head, just a couple of notes. When he’s practicing his guitar, he’d just sit around playing some small riffs; just a few notes here and there. He’ll play one, then change it up a little bit, and if it sounds better, he’ll start working with that. Over time he’ll have a few more such bits floating around in his head, and every now and then he’ll play a few that just start to flow together. At that moment he can hear the overall melody, and he has to write it down, or record it – anything to capture it before it fades. It doesn’t matter what time of day it is, or what else is happening; he can’t do anything else until he has it down on paper/tape/whatever.

Now I understood: his process for composing music was very similar to what I experience when coming up with a coding design to a given problem. I’ll play around in my mind with a few approaches I’ve used in the past, changing them around as needed to see if that would work. At some point, though, the pieces seem to align themselves into the solution I need, and I can see it clearly in my mind. At that point, I have to write down what I’m seeing before I lose it. I can remember times when I missed appointments because I was heads-down writing such a solution.

The act of creation is remarkably similar for both cases: playing around with ideas/riffs, and once the solution “appears”, a furious effort to record it. And it’s that “playing around” part that is really hard to explain to others: to them, it just looks like you’re screwing around instead of working.

I do my best thinking when I’m walking, not when I’m planted in front of a keyboard. If you’re ever stuck trying to come up with a solution, try changing what you’re doing. Go for a walk, work on your garden, vacuum the floor – anything to move away from the computer and get your body moving. That act alone helps free the brain to make connections that it might otherwise never make.

Day 44: Employed Once More!

After 3 1/2 months of unemployment, during which I submitted countless job applications, became a regular on LinkedIn, learned the routines of the Texas Unemployment Benefits system, and sat through numerous interviews, I’m excited to report that I have a new job!

In a couple of weeks I will be starting at Nvidia as a Senior Python Developer, working on the tools for their GPU cloud. I’ve met the other people on my team during the video interview process, and they all seem like a bright bunch, so I can’t wait to start working with them!

It’s been difficult these last few months. It started with the pandemic and subsequent lockdown, which has affected everyone. Then came the layoff, with DataRobot letting 25% of its workforce go, including yours truly. It really wasn’t much consolation that I was only 1 of the 40 million or so in the US who lost their job in those few weeks – it still hurt.

Still, I have had it better than most. My wife still had her job, which was super-important financially. We also had some savings, so we weren’t living paycheck-to-paycheck like so many Americans have to. And it did give me some free time to work on my photoviewer software, and practice my newly-discovered sport of disc golf. It also gave me the chance to perfect my sourdough bread technique (yeah, I know – how cliché!). But there is only so much to do when largely confined to the house.

Which is why I started this daily writing exercise. Not just to fill the time, but to get down some of the thoughts that have been in my head for a while, and polish my rusty writing skills. And while it’s been difficult to always find something to write about, I have noticed that writing itself is feeling more fluid.

I will continue this daily project until I start the job on July 20. After that, I will continue to write, but just not on a daily basis. Going through this exercise has helped me enjoy writing more, and improved my ability to let a piece out into the wild without first obsessing with endless editing. That is probably the best thing I’ve gotten out of it.

Day 43: Scarcity and Value

How do you price art?

There is one aspect of economics that everyone understands: the law of Supply and Demand. It’s pretty obvious: useful/desirable things will be valued more highly than stuff that isn’t as in demand, and scarce things will cause people to offer to pay more.

I’ve found something
No one else is looking for
I’ve found something
That there’s no use for
And what’s more
I’m keeping it to myself

Wire, Single K.O.

For this discussion let’s assume that the art in question is “desirable”, so that there is a certain level of demand for it. The determinant for price will therefore be how scarce it is.

There is a fundamental difference between a painting, in which the creative effort results in a single item, and a recording of a performance, which can be duplicated and replayed an infinite number of times. The artist can only sell their painting once, but can sell as many videos as people want.

This same issue comes up with media such as photography and print making: there really is no limit to the number of copies of a single art work that can be made. In the days of negatives, the act of making a positive print was itself part of the creative process, because the printer (usually the photographer) had to have a feel for how to balance overall exposure with local dodging and burning. The great photographer Edward Weston trained his son Cole to learn his precise printing techniques, so that Cole could continue to make prints that would be as close to the artist’s vision as possible. So while in theory an infinite number of prints could be made, there is a practical limit.

But digital photography throws all of that out the window. The artist can make whatever corrections or other changes they want to the digital file, which can then be reproduced without loss forever. So how does one determine a price for something like this?

I’ve recently begun to submit my work to several galleries, and have had some success – just yesterday I got notice that one of my photos was accepted for a show! But I’ve seen several Calls for Entry for exhibits that have a requirement that any submitted work be part of a limited edition. A Limited Edition is when the artist decides that there will only ever be a certain number of prints made, and each print is “numbered” so that they buyer knows that they are one of the few owners of that piece.

I call bullshit.

Art’s value is in the piece itself. If it moves you, makes you think, or just is stimulating to look at, it has value. The fact that only a few other people can enjoy that particular piece doesn’t change the experience; it just creates an artificial scarcity to prop up prices that otherwise can’t be justified.

Paintings are scarce, by their very nature. Digital photographs are not.

I’m not playing this game. Sure, this might keep me out of some galleries, but those are probably not compatible in spirit with me. With a calibrated monitor, I can create a digital file that can be printed exactly the same anywhere in the world. If you like my work and want a print, I will sell you a print. I won’t say “sorry, but I’ve sold all the prints I can make of that image. You’ll have to find one from some art dealer or collector”.

The digital transformation calls for new ways of thinking about art. The music business learned that lesson with the advent of the .mp3 file. The photographic business will need to grow to accommodate this new digital reality.