Make basic cipher function more readable
<p>I have this basic cipher function:</p>

<pre><code>def encrypt_decrypt(data, in_or_out):
    pass_lst = list(data)
    return_list = []

    if in_or_out == "in":
        for i in pass_lst:
            num = ord(i) + 10
            return_list.append(chr(num))
    else:
        for i in pass_lst:
            num = ord(i) - 10
            return_list.append(chr(num))

    return ''.join(return_list)
</code></pre>

<p>I want to make this cipher a little more readable and a little <code>DRY</code>er.. Is there a way I can shorten this function successfully?</p>

<p>As a general rule, functions should do <em>one</em> thing; combining two functions into one, then using an argument to trigger which "embedded" function actually runs, is a bit of an antipattern. You can still abstract out the common code (here, following PM 2Ring's definition):</p>

<pre><code>def encrypt(data):
    return _modify(data, 10)

def decrypt(data):
    return _modify(data, -10)

def _modify(data, delta):
    return ''.join([chr(ord(i) + delta) for i in data])
</code></pre>

<p>In general, your pair of functions is not going to be this symmetrical, though, and it will not be so easy to implement both in terms of one clear function. In that case, you <em>definitely</em> do not want to be stuffing both implementations into one <code>encrypt_or_decrypt</code> function.</p>

<p>(Even if you <em>do</em> combine them, don't use two separate sets of terms. Pick one of "encrypt"/"decrypt" or "in"/"out" and stick with it for both the function name and the value to pass to the argument.) </p>

<p>If you really need to choose between encrypting and decrypting based on the value of a parameter, store your two functions in a dictionary:</p>

<pre><code>d = {"encrypt": encrypt, "decrypt": decrypt}

d[in_or_out](value)
</code></pre>

python python-2.7