Technical skills acquired as part of my degree My CV focuses mostly on commercial experience. But there are many aspects of software engineering which are part of the MEng degree course and some employers may be interested in that. This document outlines some of the practical skills I learned. In the first year all students get an introduction to programming. Because I had already worked as a software developer for one year I had no trouble with imperative programming (in a Pascal-like language), but additionally students learn Haskell, Prolog and a little assembly language. (Haskell is a purely functional language, that is, there are no variables and no side effects from evaluating a function. Programming is done by writing and combining functions. With its flexible type system the language is well suited to more theoretically-based programming and prototypes.) Later on students are taught C and Java (again I already knew those) and there are some courses in compiler construction which include writing part of a small compiler. The second year also covers SQL and relational calculus, and an operating systems course which includes a programming assignment extending the Minix operating system. (Minix is a small Unixalike OS written in C; my task was to add a debugger.) After that there's usually no need to learn additional programming languages, although various courses have programming assignments done in specialized languages like S-Plus for statistics, CSP or CCS for concurrency modelling, and Z or Alloy for specifications. The software engineering courses include an introduction to UML but I have not used it for real projects. However in the third and fourth years you may learn more of the background behind languages you already know. I took courses in type systems, advanced issues in OO languages (explaining the implementation of C++ and Java bytecode interpretation), and computational logic (the semantics of Prolog and other possible deduction systems). My final year project was called 'Query languages for semistructured data'. Semistructured data, of which XML and X.500 directories are an example, is that where the schema is not wholly fixed but new fields can be added. Code written for data with a given structure may still work on data with a slightly different structure. For example, older web browsers will still accept documents using newer HTML tags, though perhaps not with the full functionality. The model of semistructured data I used was an unordered tree model. Syntactically these unordered trees are similar to the structures used in process calculi like CCS or the ambient calculus, but a better analogy might be to imagine XML where the relative ordering of elements at the same depth does not matter. There is not space here to describe the project in detail but the full report is available at . Chapter 3 of that report is an introduction with diagrams. In brief, my project involved standardizing the data model and implementing a logic to match against these trees. For each way a tree can be built (empty tree, single branch, parallel composition of two trees) there is a corresponding case in the logic. Then with the addition of logical operators and, crucially, variables, we can execute queries by finding all variable bindings such that a tree satisfies a formula. The presence of negation in the query language causes problems, since the result might be an infinite set ('find all X such that X is not a model of car' - that is very many Xs) and either you have to restrict use of negation or else find some way to handle these infinite sets. Once you have the set of variable substitutions you can instantiate a template to build a new tree from the results (analogous to the way XSL, for example, takes a tree as input and produces a tree as output). I built on earlier work handling the infinite sets produced by negation and my new contribution was handling nested queries which produce an infinite result: as long as the top-level query is finite the result can be constructed.