![]() |
![]() |
![]() |
To provide a gentle introduction to writing simple Python programs.
A major objective is to develop an understanding of "Programming", rather than simply learning to "Code in Python".
The design of Algorithms, rather than simply generating code to solve trivial Exercises, has been emphasised.
Primarily, Biologists with No Programming Background.
The obvious place to start might be the Python Home Page
There are many fine Books introducing Python to the beginner. Those I have found of particular value include:
As a swift search of the INTERNET will confirm, there are many fine Python Tutorials freely available. Amongst which is this Python Online Tutorial/Manual. Both a Manual and a Tutorial.
I have attempted a series of topics, offering Explanation (Text and Video), Examples and Exercises, to lead the user to a level of competence that should enable the design and implementation using Python of solutions to simple problems.
I have divided these topics into a number of
colour coded categories, thus:
I assume you are using some reasonably current flavour of Linux similar to Ubuntu. If you are not, it should affect very little once you are actually using Python. You might just occasionally have to think laterally when talking directly to the Operating System (for example, when downloading example files and putting them somewhere they can be accessed by your code).
I assume you are using Firefox, set to display text files in the browser. Irritatingly there seems to be no browser that behaves itself as it should 100%! Even Firefox required some bizarre manipulations (of my data/code files) to play nicely! I expect you could cope with any browser that is convenient to you, I simply suggest that Firefox might give you the easiest ride.
I assume you are using CPython, which is the default implementation of Python, written in C. I imagine you are, no need to check as all the practical elements of this tutorial should work fine what ever you are using. Only some of the background discussion will be specific to CPython.
I assume you are using Python 3.6 or better. If so, everything will work fine. If you are are using an earlier version of Python 3, that should be good enough. Just a few things might not be quite as described (particularly the ordering of Dictionaries). If you are using Python 2, you will find significant differences to the extent I would advise you to update you Python installation.
Python 3 was introduced in 2008 and so Python 2 has been "obsolete" for 10 years now. As Python 3 is significantly different to Python 2, there has been an understandable reluctance for people maintaining substantial volumes of Python 2 code to move to Python 3. However, teaching a new generation of programmers to use a Language that has not been current for a decade and from which support will soon be withdrawn (First day of 2020) does not seem to be too sensible. Accordingly, this tutorial presents Python 3 (unlike a number of other training programs you might find on the web).
Some familiarity with the UNIX Command Line will be assumed for this course. No class time will be dedicated to learning UNIX.
If you think this might be a problem for you, please make use of the materials below. They should be enough as you do not need to be a UNIX expert.
For many of you, instruction on the wonders of the UNIX Command Line will be unnecessary.
If this is the case for you, read no further, see you at the start of the course.
If you have any doubts, here is offered a short video outlining how the UNIX Files and Directories are organised and addressed.
A UNIX Command Line Tutorial is also provided. Part I of this Tutorial should provide more than enough familiarity with UNIX to meet the requirements of this Training Course.
A fffffffffffffffffffff is also provided. Part I of this Tutorial should provide more than enough familiarity with UNIX to meet the requirements of this Training Course.
Quiz question #2
3. Quiz question #3
4. Quiz question #4
In order to investigate the wonders of Python, it is essential to first to set up your computing environment in a suitable fashion.
Essentially, this means readying the software that processes Python commands for action.
This short section is comprised of a short description of the relevant software plus instruction on how to set it going in the fashion appropriate for the initial stages of the tutorial.
A Scalar Value is a single item of data.
Scalar Data Items can be one of
a variety of types including:
The two terms type and class are, these days, effectively synonyms. I will use them interchangeably in this tutorial. Historically, there was a significant difference. If you are interested, you could look here, but I would not advise doing so at this point.
In this section, all topics will be investigated using the Python Interpreter interactively.
Can you think of a simple way to include a single quote character (' or ") inside a string?
Well neither:
>>> 'A single quote ' in a string'nor:
will do!
In both cases, the quote embedded in the string is of the same type as the enclosing quotes. The Interpreter is bound to assume the embedded quote is the string terminating quote and so get a trifle confused as to what the rest of the line might be!
The solution is transparent! Simply choose the enclosing quotes to be distinct from the embedded quote. The embedded quote will then be interpreted as just another character of the string and all will be well.
>>> "A single quote ' in a string"No reason why this trick should not work for lots of Quotes of the same type.
>>> "Lots of single quotes ''''''''' in a string"The Backslash Character can be used to suppress the interpretation of characters such as Quotes.
For example, if the Interpreter
meets an embedded Quote
matching the
String enclosing Quotes,
it will incorrectly interpret
that Quote as ending the
String. However, precede the
embedded Quote by a
Backslash and
the Interpreter will dispose of
the Backslash and accept
the Quote as just another
Character.
Using this trick, any number and assortment of Quotes inside a String can be handled.
>>> print("A String with \"\'\'\"\'\" assorted, silly quotes")How would you expect the Python Interpreter to react to the gentle stimulus: '14' + '7'
How about: '14' - '7'
Note: Unfortunately the Interactive
Interpreter does not deal properly with
Escape Codes directly.
The easiest way to deal with this problem is to
introduce the use of the Built-in function
print()
to display Strings a little ahead
of schedule.
print() is more powerful than is
implied here, as you will see soon.
Super ... wonder when one would ever use that?
Remember typewriters? I suppose not.
>>> print("The barrel slides back\rbut not forward!")The first letters of the bit before the CR are obliterated by the first letters after the CR.
Exactly what happened when one's typewriter barrel returned to the left, ready for the next line (Carriage Return), but forgot to move the paper forward (a REAL Line Feed).
Basically, one achieved a mess of over typing. Used to be regarded as a bit of a disaster in the days of yore. I wonder why one needs to simulate such a mechanical failure (if a trifle more tidily) in a modern computer?
Possibly, because one can?
\n - Linefeed (LF)
A very tidy display using tabs. I am rather proud of this one. Even threw in a few Line Feeds for good luck!
Anyone spot the difference between FF and VT? Must be one surely?
Oh ...dearie dearie me!! I look it up. I receive enlightenment from one, John Bode who reveals the difference is vital to those using:
"Hardcopy Terminals and Line Printers."
John confirms the speculations of his inquirer thus:
" ... Your interpretation of Form Feed is correct; it moves to the beginning of the next page. Vertical Tab advances the page by several lines without a Carriage Return."
Gulp! ... indeed that makes a lot of sense ... but the last "Hardcopy Terminal" was eaten by a Spinosaurus, just before the Earth cooled???
Line printers??? Golly! I used to print the Royal Navy's pay cheques out on those. I had three of them that I controlled using my Hardcopy Terminal (the very one that got eaten!). I was very important back then! Mess with me Boyoh! and I lose your Pay Cheque!!
Remember cheques? Paper things you could exchange for beer.
OK, so now we all know about Form Feeds and Vertical Tabs? Jolly good.
>>> (6 == 6) and (7 == 7)
True
>>> (6 == 6) and (7 == 7) and (3 == 4)
False
>>> (6 == 6) and (7 == 7) and (3 != 4)
True
>>> ('aaa' >= '9') and ('AAA' <= '111')
False
>>> ('aaa' >= '9') or ('AAA' <= '111')
True
>>> not (6 == 7)
True
>>> not ((6 == 'a') or ('b' < 'z'))
False
>>> (not (6 == 'a') or not ('b' < 'z'))
True
>>>
A Scalar Variable can be thought of as a named "Container" in which a Scalar Value might be stored.
Scalar Variables are typed according to the Scalar Value they are assigned. That is, a Scalar Variable takes on the same type (or class) as the Scalar Value it "contains".
Loosely, with only Scalar Values we could just do "Arithmetic", adding Scalar Variables enables "Algebra".
The discussion that follows applies (unless explicitly stated otherwise) not just to Scalar Variables, but to Variables that "contain" the more complex entities that will be covered later in this tutorial.
Again, these entities will be investigated using the Python Interpreter interactively.
Note: type() is
a Python Built-in Function. That is,
a facility that Python considers to be
of great sufficient "importance" to be offered,
"ready coded", as part of the language.
We will discuss Built-in Functions, and
User Defined Functions, later and in
some depth.
I introduce type(), ahead of time as it
serves a purpose useful here and now.
type() takes a Variable as an
Argument, which is placed between the
brackets (), and it returns the type
(or class) of that Variable.
What is the difference between a=6 and a==6 ?
Try setting Three Variables (d, e and f, say) to the same Value (47.6, say) all in one line of code.
Always assuming your complete success, what is the type of e?Are Python Variable Names Case Sensitive?
In Python, "There is no difference that matters a jot!" , so its fine to skip the next bit if you wish.
Essentially, my summary, based on my best hit from many google searches, is as follows:The Scalars considered thus far enable basic Arithmetic, Algebraic and simple String manipulatory operations.
Python builds on this provision with some "ready coded" Functions that are integral to the language.
Such features are called Built-in Functions.
A more comprehensive discussion of Functions (and similar) will be offered when User Defined Functions are considered a little later. For now, a Function is a code block that (Optionally) accepts Arguments and returns a Value.
type() and print(), which you have already superficially used, are examples of Built-in Functions.
As used above, type() accepts a single Argument (a Scalar Value or Variable) and returns information revealing the Class of that Scalar.
>>> type (4.657)So far, we have used print just to display simple Strings (as Scalar Values or Variables).
>>> print("Saturday night\nJust got paid")A complete list of all Python Built-in Functions, all with very comprehensive descriptions will be useful for reference, and can be found here (amongst other places).
It would not be useful to try and describe them all here! Instead, I suggest we introduce a few of the more vital examples and add other as the need arises (via Examples, Questions and Exercises)
The "breaks" cannot be placed
just anywhere.
You must choose a place that is
not going to confuse the
Interpreter too much.
In the example above, I chose the
end of each line of the Limerick,
which worked fine!
A method is a Function that is specific to a particular Python Data Class (or type).
Of the Data Classes discussed so far, only Strings really have and interesting range of methods.
Accordingly, here it is the plan to start by looking at a few examples of String methods, to get the general idea, and the to discuss further methods as more the complex Data Classes are introduced.
If you did wish to generate a list of all the available methods for a given Class, it is very easy. Just use the Built-in Function help(). For example, to list all the String methods, type:
help(str)Try it.
What choice!! Have I missed any?
Aside 2:
Many of the methods listed have names beginning and ending with underscores
.
A fine summary of the philosophy of using underscores at either and of Variable Names can be found here. A neat summary of the relevant section of the Python Style Guidelines.
Summarising further, for the purpose of this tutorial, I think it is OK to ignore anything with Underscores at either end of its Name. Particularly those with Double Underscores at both ends ("essentially reserved for Python itself") and to resist using leading and/or trailing Underscores for Variable Names you create.
Input and Output from files stored on external storage devices (almost inevitably some sort of Disk these days) relies on a Built-in File to create a "File Handle" (or a File Object if you prefer).
Once the File reference is created, accessing the file is exclusively (as far as this tutorial is concerned) accomplished using methods associated with File Objects. This being so provides a good excuse to cover File I/O here, while discussing the most important File Object methods.
Displaying the complete list of methods available for a File Object with help() is not straight forward. file is not a simple single class. However, help() will work successfully on an instance of a File Handle.
So you could create a File Handle with the Built-in Function open and the give that File Handle to help().
The trouble with that plan, is you probably have no file handy to open!
No problem! We cannot be defeated! So open a file specifying that you wish to WRITE to it (so it does not need to already exist). Then use help() on that, hopefully new and empty, file. Clever eh!?
>>> Empty_File=open("TEST", 'w')It is the 'w' bit of the open command that requests a file for writing rather than just reading (the default)
Try it ... or for the less adventurous, the entire list can be found here.
There are four ways of request the execution of a method. The first two are the more common. Informally the alternatives are:
An example requires exposure to at least one particular method.
OK, title is a method of the Class str.
It capitalizes the first letter of each word of the String it processes. It needs no Arguments except the String to be capitalized.
The four options, in order, would be:
Interesting that title makes the 't' of 'don't' upper case? Perhaps a protest against the ghastly truncation? It certainly does not seem quite correct even so.
Thanks to Groucho (Marx that is) for the gloriously flexible ethics.
It is Important to Note:All
String methods return new values.
They do not change the original String.
Method | Effect |
---|---|
str.lower() | Returns a string with Upper Case Characters converted to Lower Case. |
str.casefold() | Returns a string with Upper Case Characters converted to Lower Case. Generally used for caseless matching. This is more aggressive than the lower() method. |
str.upper() | Returns a string with Lower Case Characters converted to Upper Case. |
str.swapcase() | Returns a string with Lower Case Characters converted to Upper Case and vice versa. |
str.capitalize() | Returns a string with first letter capitalized and the rest in Lower Case. |
str.title() | Returns a Title Cased String (first character of each word capitalized, others Lower Case). |
There are far too many str methods (methods in general even) to try and include all in a sensible number of short exercises. I aim for a representative few.
If you wish to know more about any I omit, I draw your attention to the Links I have embedded in the method Tables (and the List of methods in the Checkpoint section).
These take you to the section of the
Python manual that
describes, fully, each method.
Method | Effect |
---|---|
str.ljust() | Returns a String Left Justified within the specified width, with optional Fill Characters. |
str.rjust() | Returns a String Right Justified within the specified width, with optional Fill Characters. |
str.center() | Returns a String Centred within the specified width, with optional Fill Characters. |
str.lstrip() | Returns a String with specified leading characters removed. |
str.rstrip() | Returns a String with specified trailing characters removed. |
str.strip() | Returns a String with specified leading and trailing characters removed. |
Method | Effect |
---|---|
str.isalnum() | Returns True if the String is non-empty and all characters are Alphanumeric. |
str.isalpha() | Returns True if the String is non-empty and all characters are Alphabetic. |
str.isdecimal() | Returns True if the String is non-empty and all characters are Decimal Characters. |
str.isdigit() | Returns True if the String is non-empty and all characters are Digits. |
str.isnumeric() | Returns True if the String is non-empty and all characters are Numeric. | str.islower() | Returns True if all the the Cased Characters of the String are Lower Case and there is at least one Cased Character. |
str.isupper() | Returns True if all the the Cased Characters of the String are Upper Case and there is at least one Cased Character. |
str.isprintable() | Returns True if the String is empty or all characters are Printable. |
str.isspace() | Returns True if the String is non-empty and all characters are Whitespaces. |
str.istitle() | Returns True if the String is non-empty and Title Cased. |
str.isidentifier() | Returns True if the String is a Valid Identifier. |
Method | Effect |
---|---|
str.replace() | Returns a String in which all instances of one specified substring of the original String is replaced by with another. |
replace() requires 2 Mandatory
Arguments and accepts a third Optional Argument.
You will need either to be good at guessing, or to look
these up before proceeding.
Note: The inclusion of Comments
in the code. That is, lines commencing with
'#' Characters. These will be
ignored by the Interpreter.
Not really practical when using the
Interactive Interpreter to execute one
command at a time, but vital when
writing blocks of code (Programs)
to be stored more permanently in disk files
and used repeatedly.
There is an alternative approach (better?) to Complement a Sequence. We will look again at this task when we have the requisite tools.
The way to do this is very neat. I
involves Slicing the Forward Complement
in a particular way.
I admit that the reason I did not include
Reversing previously, is that I have only just
discovered how to do it nicely without using
things we have yet to discuss.
Have a quick struggle before you press
the Answer button.
The code for a str in a formatted print string is %s.
Run it from the command line. You now have a permanent (immensely crude) program to generate the reverse and complement of any sequence you imagine.Method | Effect |
---|---|
str.count() | Returns the number of non-overlapping occurrences of a given substring within a String. |
str.startswith() | Returns True if the String starts with a given substring. |
str.endswith() | Returns True if the String ends with a given substring. |
str.find() | Returns the Index of the first occurrence of a substring in the String. Returns -1 if not found. |
str.index() | Returns the Index of the first occurrence of a substring in the String. Raises an Error if not found. |
str.rfind() | Returns the Index of the last occurrence of a substring in the String. Returns -1 if not found. |
str.rindex() | Returns the Index of the last occurrence of a substring in the String. Raises an Error if not found. |
OK, I have cheated a lot!!! There is only one Stop Codon and it is in frame. This allows me to ignore any possibility of error anywhere! Maybe a bit more reality later?
>>> #
In fact, you may well be feeling that many of these exercises
would be easier to code in a file and run from the command line?
The Interactive Interpreter is perchance beneath you, now you
have acquired such advanced programming skills.
If such be the case, then feel free to solve exercises in the
fashion you deem to be most suitable. I will continue to use
the Interactive Interpreter for a while longer (explicitly
suggesting a "program file" approach where it is particularly
appropriate).
To make this one run half way sensibly, I had to massage the code in lots of ways I did not want to! I cheated a lot in the Interactive version.
Method | Effect |
---|---|
str.format() | Returns the formatted String. |
I consult higher authorities and the
consensus is that the reasons for this
restriction are practical rather than
logical.
That is, the goal is to improve
efficiency rather than to avoid
logical inconsistency.
Intuitively, it would certainly seem to
be a greater task for the Interpreter
if all positional Arguments were
not assured to be in an unbroken series
from 0 to N?
Method | Effect |
---|---|
file.read() | Reads at most, a specified number of Bytes (Characters) from the File (less if the read hits EOF early). |
file.readline() | Reads one entire Line from the File. A trailing newline Character is kept in the String. |
file.readlines() | Reads until EOF using readline() and return a list of Lines. |
file.write() | Writes a String to the File. |
file.writelines() | Writes a sequence of Strings to the File. |
file.close() | Close the File. A closed File cannot be read from or written to. |
It seems odd there is no file.writeline()?
The clearest explanation (that I am not sure I follow entirely) is
here.
I only mention this as I imagine you might spot the lack of symmetry.
It really does not matter in the context of what we are trying to achieve.
Use file.write() several times rather
than file.writelines().
The reason for this advice will become apparent when
you have got just a little further on in the tutorial.
Note: file.write() will not
append a newline to the String it outputs.
If you want a newline, you must explicitly
include it in the String.
Note
The line:
Line=Line.rstrip('\n')
What does this acheive? Try commenting it out and see what difference it make to the output.
Method | Effect |
---|---|
list.copy() | Returns a copy of the list. |
Method | Effect |
---|---|
list.clear() | Removes all the elements from the list. |
list.append() | Adds an element at the end of the list. |
list.extend() | Add the elements of a specified list (or similar), to the end of the current list. |
list.insert() | Adds an element at the specified position. |
list.pop() | Removes the element at the specified position. |
list.remove() | Removes the first item with the specified value. |
list.sort() | Sorts the list. |
list.reverse() | Reverses the order of the list. |
Method | Effect |
---|---|
list.count() | Returns the number of elements with a specified value. |
list.index() | Returns the index of the first element with a specified value. |
Being immutable, a tuple will take up less
memory that an equivalent list.
In particular, whereas a tuple is of fixed
memory requirement,
an equivalent list will allow extra memory for
possible expansion.
Also due to its immutability, access to a tuple
is faster
than to an equivalent list.
Conceptually, the only real difference between
lists an tuples is mutability.
However, in the ways Python chooses to implement
these two different Data types, there are greater,
more profound, distinctions.
There are many occasions where either
a list or a tuple would suit the
purpose of a program.
In general, it is thought best to use a tuple
unless mutability is imperative.
Method | Effect |
---|---|
tuple.count() | Returns the number of elements with a specified value. |
tuple.index() | Returns the index of the first element with a specified value. |
Of course you can still
duplicate Pointers to a single
tuple by Assignment.
Just not too sure why you would ever want to?
>>> Tuple_Original=('a','b',6,8,43.7)
>>> Tuple_Copy=Tuple_Original
>>> print(Tuple_Original,Tuple_Copy,sep='\n')
('a', 'b', 6, 8, 43.7)
('a', 'b', 6, 8, 43.7)
>>>
Is this the first time we have seen
that one can put more than one command
on a single line if they a separated by semicolons?
I think so! I will claim it in the Checkpoint
Section anyway.
A number of languages insist that all commands are
terminated by semicolons. In fact, Python does not
object if you terminate all commands with semicolons
... or not ...
I rather like lots of semicolons, but it
is not common practice with Python Programmers,
so I restrain myself to conform.
The nature of a range is something
that changed radically between
Version 2 and Version 3 of Python.
In Python Version 2, the
range() function
simply returned a list.
Conceptually much simpler for the user, but the
developers of Python 3
clearly opined that the
gain in memory efficiency was worth the
introduction of the range type.
So we users have to struggle a
little harder to
understand exactly what is going
on? Well, only
a little, thinking of a range
as a tuple (rather
than a list) is sloppy,
but it only breaks down
if you try to print the
range out without
first casting in to a list
of tuple.
Python 2.7.12 (default, Dec 4 2017, 14:50:18)
[GCC 5.4.0 20160609] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>>
>>> Python2_range=range(10)
>>>
>>> type(Python2_range)
<type 'list'>
>>>
>>> print(Python2_range)
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
>>>
Method | Effect |
---|---|
range.count() | Returns the number of elements with a specified value. |
range.index() | Returns the index of the first element with a specified value. |
A Note on the Ordering of a Python Dictionary
Until very recently, Dictionaries were
regarded as Unordered.
Indeed the Key-Value pairs do not need to be
in any specific Order to enable their prime function.
That is, to access a Value by quoting its Key
(as you might use a word, "Key", to access a meaning,
"Value", in a conventional Dictionary)
Python uses the Dictionary Key
(unlike with a conventional Dictionary, in a fashion
that does not require the Keys to Ordered)
to find and deliver the corresponding Dictionary Value.
However, as I hope will be illustrated in an
exercise (the one involving the use of dict.popitem()),
Dictionaries do have a logical
Order for their Key-Value Pairs.
From Python 3.6 onwards Dictionaries were
declared to be Ordered,
seemingly without too much guarantee of consistency!?
Happily, since then the move has been made
"officially" part of the Python Language Specification
and so should be reliable in all Python Implementations,
from Python 3.7 (current stable version) onwards.
A Python Dictionary is implemented as a Stack,
which has a natural Last In First
Out (LIFO) order of access.
Think of the Dictionary as a tower (Stack)
of Key-Value Pairs.
New Dictionary elements (Key-Value Pairs)
are added to ("pushed on") the Dictionary
by being placed on the top of the tower.
When Dictionary elements are removed,
the easiest (only sensible?)
way is to remove ("pop") them from the top of the tower.
That is, the Last One to be added is
the First One to be removed
... hence Last In
First Out (LIFO).
Method | Effect |
---|---|
dict.copy() | Returns a copy of the Dictionary. |
dict.fromkeys() | Returns a Dictionary with the specified Keys and optionally specified single Value (default None). |
Method | Effect |
---|---|
dict.clear() | Removes all the elements from the Dictionary. |
dict.setdefault() | If the specified Key is not already in the Dictionary, it is added with the specified Value. Returns the Value of the specified Key. |
dict.update() | Updates the Dictionary by appending the specified Key-Value pairs. |
dict.pop() | Removes the element with the specified Key. |
dict.popitem() | Removes the last Key-Value pair to be added to the Dictionary. |
Method | Effect |
---|---|
dict.get() | Returns the Value of the specified Key. |
dict.items() | Returns a list containing a tuple for each Key-Value pair. |
dict.keys() | Returns a list containing a Dictionary's Keys. |
dict.setdefault() | If the specified Key is not already in the Dictionary, it is added with the specified Value. Returns the Value of the specified Key. |
dict.values() | Returns a list of all the values in the Dictionary. |
There is also a Data type frozenset,
which is simple a immutable
version of a set.
So set is to frozenset
as list is to tuple.
The main justification of
frozensets is to allow sets to
include set Elements.
Python will not allow a normal set to
include a set as sets are mutable
(and so not hashable in Python).
However, a set MAY include a frozenset,
as it is immutable (and so Python hashable)
and is in all ways that normally matter,
the same as a set.
That is all I will say about frozensets,
unless I can think of a neat exercise
that needs one of course.
Method | Effect |
---|---|
set.copy() | Returns a copy of a set. |
set.difference() | Returns a set containing the Difference between two or more specified sets. |
set.intersection() | Returns a set, that is the Intersection of two specified sets. |
set.symmetric_difference() | Returns a new set which is the Symmetric Difference (or Disjunctive Union) of a set and one other specified set. The Disjunctive Union of two sets is computed using the Exclusive OR (XOR) Boolean Operator. |
set.union() | Return a new set that is the Union of a set and other specified set(s). |
Method | Effect |
---|---|
set.clear() | Removes all the elements from a set. |
set.discard() | Remove the specified item. If no element matches the specification, no action is taken. |
set.remove() | Removes a specified element from a set. If no element matches the specification, an Error State ensues. |
set.pop() | Returns and Removes a random element from a set. |
set.add() | Adds an element to a set. |
set.difference_update() | Removes the items in a set that are also included in another, specified set. That is, updates a set to the Difference between it and another set. |
set.intersection_update() | Removes the items in this set that are not present in other; specified set(s). That is, updates a set to the Intersection between it and another set. |
set.symmetric_difference_update() | Replaces a set by its Symmetric Difference (or Disjunctive Union) with one other specified set. The Disjunctive Union of two sets is computed using the Exclusive OR (XOR) Boolean Operator. |
set.update() | Update a set with its Union with other specified set(s). |
Method | Effect |
---|---|
set.pop() | Returns and Removes a random element from a set. |
Method | Effect |
---|---|
set.isdisjoint() | Returns True if two specified sets have a non-empty Intersection, False otherwise. |
set.issubset() | Returns True if another specified set contains this set, False otherwise. |
set.issuperset() | Returns True if this set contains another specified set, False otherwise. |
AA_Codes = { 0:"Arginine - Arg - R", 1:"Lysine - Lys - K", 2:"Aspartic acid - Asp - D", 3:"Glutamic acid - Glu - E", 4:"Glutamine - Gln - Q", 5:"Asparagine - Asn - N", 6:"Histidine - His - H", 7:"Serine - Ser - S", 8:"Threonine - Thr - T", 9:"Tyrosine - Tyr - Y", 10:"Cysteine - Cys - C", 11:"Tryptophan - Trp - W", 12:"Alanine - Ala - A", 13:"Isoleucine - Ile - I", 14:"Leucine - Leu - L", 15:"Methionine - Met - M", 16:"Phenylalanine - Phe - F",17:"Valine - Val - V", 18:"Proline - Pro - P", 19:"Glycine - Gly - G"}
if Random_AA <= 3: print("Charged (side chains often makes salt bridges)") if Random_AA > 3 and Random_AA <= 11: print("Polar (usually participates in hydrogen bonds as proton donor/acceptor)") if Random_AA > 11: print("Hydrophobic (normally buried inside the protein core)")
AA_Codes = { 0:"Arginine - Arg - R", 1:"Lysine - Lys - K", 2:"Aspartic acid - Asp - D", 3:"Glutamic acid - Glu - E", 4:"Glutamine - Gln - Q", 5:"Asparagine - Asn - N", 6:"Histidine - His - H", 7:"Serine - Ser - S", 8:"Threonine - Thr - T", 9:"Tyrosine - Tyr - Y", 10:"Cysteine - Cys - C", 11:"Tryptophan - Trp - W", 12:"Alanine - Ala - A", 13:"Isoleucine - Ile - I", 14:"Leucine - Leu - L", 15:"Methionine - Met - M", 16:"Phenylalanine - Phe - F",17:"Valine - Val - V", 18:"Proline - Pro - P", 19:"Glycine - Gly - G"}
if Random_AA <= 3: print("Charged") else: if Random_AA > 3 and Random_AA <= 11: print("Polar") else: if Random_AA > 11: print("Hydrophobic") else: print("I do not beleive you!")
AA_Codes = { 0:"Arginine - Arg - R", 1:"Lysine - Lys - K", 2:"Aspartic acid - Asp - D", 3:"Glutamic acid - Glu - E", 4:"Glutamine - Gln - Q", 5:"Asparagine - Asn - N", 6:"Histidine - His - H", 7:"Serine - Ser - S", 8:"Threonine - Thr - T", 9:"Tyrosine - Tyr - Y", 10:"Cysteine - Cys - C", 11:"Tryptophan - Trp - W", 12:"Alanine - Ala - A", 13:"Isoleucine - Ile - I", 14:"Leucine - Leu - L", 15:"Methionine - Met - M", 16:"Phenylalanine - Phe - F",17:"Valine - Val - V", 18:"Proline - Pro - P", 19:"Glycine - Gly - G"}
if Random_AA <= 3: print("Charged (side chains often makes salt bridges)") elif Random_AA > 3 and Random_AA <= 11: print("Polar (usually participates in hydrogen bonds as proton donor/acceptor)") elif Random_AA > 11: print("Hydrophobic (normally buried inside the protein core)") else: print("If you ever get here, something is seriously wrong!")
Valid_YES = ('Y','YES','AFFIRMATIVE','QUITE','ABSOLUTELY') Valid_NO = ('N','NO','NEGATIVE','NEVER','I BEG TO DIFFER')
if Response in Valid_YES: print("So very glad you agree dear chap!") elif Response in Valid_NO: print("I am mortified that you cannot see the splendour that surrounds thee!") else: print("You answer neither Yes not No? Maybe you cannot make your mind up?")
For this section, it will be assumed that you are familiar with the types of Loop Structure that can be incorporated in an Algorithm.
We offer a short Video to discuss as much of these issues as is relevant here.
Class time will not be allocated to this material, so you are urged to take a few moments to go through the Video before the class starts.
The video - Improving Algorithm Design
by the use of Repeat Structures (Loops)
Loops - A video
In outline, the patterns for all Python Loops are disarmingly straight forward.
The basic For Loop is of
the form:
Message_Coded = ( # The Coded message.
79, 110, 101, 39, 115, 32, 77, 111, 106,
111, 32, 105, 115, 32, 102, 117, 110, 99,
116, 105, 111, 110, 97, 108, 44, 32, 97,
115, 32, 105, 115, 32, 111, 110, 101, 39,
115, 32, 74, 111, 104, 110, 32, 116, 104,
101, 32, 67, 111, 110, 113, 117, 101, 114,
111, 111, 46, 10, 97, 115, 32, 115, 112,
101, 99, 105, 102, 105, 101, 100, 32, 111,
112, 116, 105, 109, 97, 108, 32, 98, 121,
32, 116, 104, 101, 32, 105, 110, 101, 115,
116, 105, 109, 97, 98, 108, 101, 32, 77,
117, 100, 100, 121, 32, 87, 97, 116, 101,
114, 115, 46, 10, 65, 108, 108, 32, 105,
115, 32, 119, 101, 108, 108, 32, 119, 105,
116, 104, 32, 116, 104, 101, 32, 119, 111,
114, 108, 100, 32, 46, 46, 46, 32, 66,
121, 32, 116, 104, 101, 32, 76, 111, 114,
100, 32, 72, 97, 114, 114, 121, 33, 10)
The basic While Loop is of
the form:
There is no special syntax for this type of Loop. If you want to implement one, you need to "bend" what Python provides for other forms of Loop.
The easiest way to do this is to use a While loop with a <Conditional Expression> that always evaluates to True. That is a While Loop that, it left to its own devices, would continue to Loop forever!
In addition, an explicit <Conditional Expression> is added at the end of the Loop to detect the appropriate moment to leave.
The Python command break is used to request the jump out of the Loop's natural inclination for perpetual revolution.
Not particularly pretty, but it works fine
and looks something like the following:
And now ... a short quiz on the consideration
of loops and related matters, so far.
Wait until the Delivery
version is ready and then
login to Room 32COU as a Student.
Click here for the quiz.
Note, that the pseudo-code appears to be suggesting a Test at the Bottom Loop here. Maybe it should be? ... from an Algorithmic view of things? But given the way Python inclines one to view the situation, a For Loop is the more appropriate way to go in this case.
The Answer to both these Questions is the same.
# Revised Pseudo-Code: # # Import the code features that allow remote file access # Open the file from Uniprot # # Read the first Line of the file (into the variable Line) # # While the file is not exhausted (i.e. Line is not empty) # Print the current line (without decoding or explicit Newline) # Read the next line of the file (into the variable Line) # # Tidily close the remote file ################################################################## import urllib.request # import the code to access remote files. # Open remote file for reading File_URL = 'http://www.uniprot.org/uniprot/P12931.fasta' Sequence_file = urllib.request.urlopen(File_URL) Line = Sequence_file.readline() # Read the first line using readline() while Line: # While the contents of Line are not empty, print(Line) # print the current Line, Line = Sequence_file.readline() # read the next line using readline(), # go round for more. Sequence_file.close() # Close file tidily.
# Revised Pseudo-Code:
#
# Import the code features that allow remote file access
#
# Stage 1 (Outline only)
# ======================
#
# Open the file from Uniprot
# Open a local file for writing in binary
#
# Read the remote file, write it to an identical local file
# Print each line without decoding as it is read
#
# Close both the remote input file and the local output file
#
# Stage 2
# =======
#
# Open the local input file for reading in binary
#
# Print each line as it is read
# Report the type of the first line
#
# Tidily close the local input file
#
# Stage 3
# =======
#
# Open the local input file for reading in binary
#
# Print each line decoded as UTF-8 (the default Character encoding)
# Suppress the EOL that print() would append by default
#
# Close the local input file
#
# Stage 4 (Just for fun, this generates nonsense!)
# ================================================
#
# Open the local input file for reading in binary
#
# Ensure each Line is comprised of an even number of bytes
# (essential for a two byte encoding)
#
# Print each line decoded as UTF-16
#
# Close the local input file
#
##################################################################
import urllib.request # import the code to access remote files.
print("\n\n########################################################")
print("#")
print("# Step 1: Read Remote File and print its lines as read (i.e. as Byte Stream)")
print("# also write lines to a Local File Copy")
print("#")
print("########################################################\n\n")
# Open remote file for reading.
File_URL = 'http://www.uniprot.org/uniprot/P12931.fasta'
Sequence_file = urllib.request.urlopen(File_URL)
# Open a Local file for writing in binary to receive a copy of the remote file.
Sequence_file_local = open("P12931.fasta","wb")
Line = Sequence_file.readline() # Read the first line using readline().
print("The first line of the remote input file is of type: ",type(Line),end='\n\n')
# Display the type of the Byte Stream Line.
while Line: # While the contents of Line are not empty,
Sequence_file_local.write(Line)
# write the current Line to a local file,
print(Line) # print the current Line,
Line = Sequence_file.readline() # read the next line using readline(),
# go round for more.
Sequence_file.close() # Close the input file tidily.
Sequence_file_local.close() # Close the output file tidily.
print("\n\n########################################################")
print("#")
print("# Step 2: Read Local Files and print its lines as read (i.e. as Byte Stream)")
print("#")
print("########################################################\n\n")
# Reopen the Local file for reading in binary.
Sequence_file_local = open("P12931.fasta","rb")
Line = Sequence_file_local.readline() # Read the first line using readline().
print("The first line of the local input file is of type: ",type(Line),end='\n\n')
# Display the type of the Byte Stream Line.
while Line: # While the contents of Line are not empty,
print(Line) # print the current Line,
Line = Sequence_file_local.readline()
# read the next line using readline(),
# go round for more.
Sequence_file_local.close() # Close the output file tidily.
print("\n\n########################################################")
print("#")
print("# Step 3: Read Local Files and print its lines decoded to UTF-8")
print("#")
print("########################################################\n\n")
# Reopen the Local file for reading in binary.
Sequence_file_local = open("P12931.fasta","rb")
Line = Sequence_file_local.readline() # Read the first line using readline().
while Line: # While the contents of Line are not empty,
print(Line.decode("utf-8"), end='')
# print the current Line decoded to UTF-8,
Line = Sequence_file_local.readline()
# read the next line using readline(),
# go round for more.
Sequence_file_local.close() # Close the output file tidily.
print("\n\n########################################################")
print("#")
print("# Step 4: Read Local Files and print its lines decoded to UTF-16")
print("#")
print("########################################################\n\n")
# Reopen the Local file for reading in binary.
Sequence_file_local = open("P12931.fasta","rb")
Line = Sequence_file_local.readline() # Read the first line using readline().
while Line: # While the contents of Line are not empty,
print((b' ' + Line).decode("utf-16"))
# print the current Line decoded to UTF-16,
# As UTF-16 decodes bytes in pairs,
# ensure the line length is even.
# For this file, the simplest way to
# do that is to prepend a single byte
# (b' ') to every line.
Line = Sequence_file_local.readline()
# read the next line using readline(),
# go round for more.
Here are a few exercises (with solutions) for you to try.
Remember to provide pseudo-code with each answer, even though the simplicity of these exercises might make that seem a little redundant.
Why not include your pseudo-code in your Python Script as a comment?
Be sure to comment your Python Code liberally and to, wherever possible, use Variable Names that relate to their use.
Code Annotation is vital if you wish to remember what the Script you wrote a month ago was supposed to do!
"Good practice from the start" is the watchword!
Write code to read in the file
reads.fastq one line at a time and
then print out only the sequence
Annotation Lines
(the ones that start with a '@').
When the entire file is read, print out the
number of Reads it contains.
Answer.
Output is (at the top):
Output is (at the bottom):
Comments include:
What these lines are is explained in the second half of the video
I offered a while back (which I have not yet finished).
Their existence means you have to be a bit cleverer than
I have been here if you
want to count the number of reads.
For this particular file, you can improve things by counting
lines that begin "@SRR". But even this is not fool proof.
Other lines could begin "@SRR" too,
if you were outrageously unlucky.
This strategy WILL however, suffice for the
next stage of this simple(?) exercise.
Part (iii)
Using the Python command break,
Amend the code of Part (ii) so that
only the reads with Annotation Lines
less than @SRR1030347.124000
are printed.
It is safe to assume that the reads are
strictly ordered by their
Annotation Lines.
Count the reads with Accession codes less than
@SRR1030347.124000 and those with
Accession codes
greater than or equal to @SRR1030347.124000.
Display the counts along with a Grand Total
once the entire file is read.
Answer.
Output is (at the top):
Output is (at the bottom):
Comments include:
I need to think how to react ... for now I will
explain the answer live, if required.
Is it good to find lots of interesting
problems?
Or do they just get it the way of the
Basic message?
I think, a bit of both, but one needs
SIMPLE exercises
to precede the challenging ones!
For this section, it will be assumed that you are familiar with the types of Callable Unit that can be incorporated in an Algorithm.
We offer a short Video to discuss as much of these issues as is relevant here.
Class time will not be allocated to this material, so you are urged to take a few moments to go through the Video before the class starts.
The video - Improving Algorithm Design
using Callable Units
(Procedures, Functions).
Functions - a Video
In class, we will conduct a short quiz on the
content of the video and related matters.#
Wait until the Delivery
version is ready and then
login to Room 32COU as a Student.
Click here for the quiz.
Python offers a number of "Built in" functions. For example:
The number of available functions is greatly expanded by importing modules. For example:
But there will always be the instance where the exactly appropriate function for a particular user need is not available.
The only option is for the user to write that which is required him/herself. which is really very easy!
The basic syntax is as follows:
Note:
Function_Name is determined by the user,
of course;
There may be between none and
lots of parameters
( (par1, par2, par3 ...) ).
There may be between none and
lots of returns. If none,
it could be argued that what had been written
was a User Defined Procedure. Just
one return at the end of the code is typical.
{Hint:
To declare a Parameter that
can receive multiple Arguments,
you simply prepend a "*" to the
Parameter name. For example:
Average (*Numbers):
The Parameter can then be treated as
a list within the body of
the Function.
{Hint:
A Default Value is set up for a
Parameter simply by adding the
Default Value after the
Parameter Name, preceded by an
"=" sign.
In this case, the def line for
the function might look something like:
def rnatoaa(rna, Reading_Frame = 1):
rna is a Required Parameter,
for it to be omitted would be an Error.
Reading_Frame is an Optional
Parameter, if no Argument is
provided, a value of 1 will
be assigned.
Here are a few exercises (with solutions) for you to try.
Remember to provide pseudo-code with each answer, even though the simplicity of these exercises might make that seem a little redundant.
Why not include your pseudo-code in your Python Script as a comment?
Be sure to comment your Python Code liberally and to, wherever possible, use Variable Names that relate to their use.
Code Annotation is vital if you wish to remember what the Script you wrote a month ago was supposed to do!
"Good practice from the start" is the watchword!
My answer is: here
{Hint: A Recursive Function is one that calls itself. A reminder of what a Fibonacci Number is.
If you are now muttering to yourself "Recursion? Fibonacci? I do not remember discussing these?". Not Fair!Simply put all the functions made so far in a file and include the file in lots of different ways
Maybe a short video on why it is a good idea? When it is appropriate why it is structured programming
EXERCISE BODY