27 October 2006

Semantics versus Syntax

Syntax refers to the grammatical structure of a language. For example, the English language includes nouns, verbs, adverbs, and adjectives. Depending on the position and conjugation of the words in a sentence, the sentence may have correct syntax, but still be nonsensical because of the logical content of the sentence. The canonical example is "Colorless green dreams sleep furiously," which uses valid syntax--[adj] [adj] [noun] [verb] [adverb]--but is nonsense because it violates several rules of semantics.

Semantics, therefore, refers to the logical content of a sentence. As we can see, "Colorless green dreams sleep furiously" could be translated into many languages (Les rêves verts sans couleur dorment furieusement), but still have the same problems of semantics: green and colorless are mutually contradictory attributes, while it is absurd to speak of dreams sleeping, even in a poetic sense.

23 October 2006

Content Management Software

Content Management Software (CMS) is a broad category for software; it's used to organize and arrange the data files used in media of various kinds, such as online news sites, blogs, wikis, and so on. That's a pretty large subject, and those with a vocational interest in CMS applications are likely to discover that the huge range of CMS products reflects a huge range of CMS markets, with incomparable subdivisions.

CMS applications are usually very closely related to database management software; it has a backend that consists of content being managed, and a frontend that consists of the query (search) feature, display feature, or reporting feature. Hereafter, I'll be referring to the back end as the "content management application" (CMA) and to the front end as the "content delivery application (CDA)."

Not all CMS apps fit into the database format, though; for example, Movable Type and PmWiki are two common file-based applications.1 Movable Type is a very popular blogging software which users install on their personal webhost; PmWiki is a WikiEngine that users can install on their host for the creation of stand-alone wikis. In a file-based CMS, the software generates a new static page, which hereafter has a permanent address of its own.

Both file-based and database-oriented CMS apps have their virtues. The big advantage of the database design is that it is really suited to sites with immense numbers of entries. For example, while I don't know for certain, I strongly suspect that Blogger (this site) has over a 10 million individual posts. Often I have links to a particular post, which then appears as a stand-alone page. One can also pull up all my entries for the month of August 2005. In Movable Type, where I have another blog, one may also pull up posts organized by category. I naturally had an interest in including each post in as many topic categories as possible. My host was quickly maxed out because Movable Type would accomplish this by making a separate page for each way of organizing posts, which meant each post had to be stored many times; moreover, a static page has to include all of the junk on the side, the logo at the top, and the Perl scripts for comments. If Blogger worked that way, the site would be impossibly expensive to run. Instead, the blog engine (frontend) actually generates a page from fields in a vast table. Of of the columns of that table includes the text you are reading right now. Another column includes the date, while another includes settings I selected, like "allow reader comments."

File-based software has the advantage that hosting is simpler. If there are relatively few pages in the site (under a thousand), it's not a serious problem if every page the visitor could see is its own permanent file. The hosting software is simpler, and backups or modifications are easier.2

Features of CMS typically include CSS and XML, which determine the appearance of all pages without the user having to laboriously enter the HTML for each page. So, for example, the CSS for Blogger ensures that, unless I specify otherwise in an HTML tag, all text will be in Georgia font, and the background will be a certain color.___________________________________________________________1 "Movable Type vs. ExpressionEngine — A comparison," François Nonnenmacher, 2004; WikiMatrix-Compare Them table.

2 WikiMatrix--Compare Them All. I actually think modifications of the file templates are much easier if you've got a database CMS. Movable Type has templates that can be modified with a minimal knowledge of Perl, but editing the contents of each page requires that you individually visit each page and change it. In a database CMS, it's possible to access all page content through the page content table. You can insert fields and have those fields updated en masse whenever the data that belongs in it is updated.

Another important feature that I appreciate about database CMS designs is that archiving is totally flexible. Using Movable Type again--it can organize archived posts by month, week, topic, and individual; but it has to have a permanent file for each. If you create a post filed under multiple topics, then your host has to store many copies of the exact same HTML. That's absurd. In contrast, Blogger (which is not a stand-alone CMS) can simply create an entirely new archive just by entering a search query. Of course, Blogger's busy servers don't save anything--they just upload the archive to your Temp file, just like anything else you download.___________________________________________________________

22 October 2006

Unified Modeling Language (UML)

In order to program objects, a standard is required for ensuring that the objects will not interfere with each other. A modeling language can be loosely described as a "meta-language," or abstract representation of language for software designing purposes. Initially, modeling language was considered to be part of the programming technique; programming teams might follow basic guidelines so they could communicate with each other. Gradually, the various modeling languages converged into a standard that is universally taught. One of the benefits of this has been the creation of an open-sourcelibrary of software objects and tools that can be adapted readily to a core program.

In 1997, the Object Management Group (OMG) released the first version of the Unified Modeling Language (UML), which probably contributed to the subsequent popularity of OOP. Initially, the paucity of open-source objects posed a problem; in order to create large numbers of mutually compatible applications based on objects, one needs an immense number of program objects for all the detailed subroutines that a full-fledged application comprises. Object-oriented programming is especially unsuited to the conventional variety of intellectual property rights, since proprietary objects can only be used by the original developer, or else, require complex licensing agreements. The UML seems to have had its greatest impact in the rapid and impressive development of the online content management software (CMS) since '04, most notably Drupal.

The UML is a set of freely available standards (download) that are roughly analogous to any number of industrial methodologies (TQM, etc.). From these standards have evolved a large number of UML development tools, most notably the UML diagrams.

Click on image for larger view

The illustration above is a screencapture of a program called Pacestar UML Diagrammer, whose purpose--shockingly enough--is to generate UML diagrams. There are 13 diagram types; the one shown in the active window above is a class diagram, with a case diagram in the background. All thirteen are listed below, with links to an excellent site explaining their purpose. As one realizes the complexity of the symbolic language that was developed for UML,one begins to understand the sweeping importance UML has had on modern (post-2004) software design. Firstly, UML 2.0 (released that year) was the industry standard for symbolic analysis of the operation, architecture, and functionality of object oriented software; secondly, new software applications tend to be object-oriented; and thirdly, OOP was becoming much more popular than it had been in the past precisely because UML was increasing the ease of OOP relative to softwares for which something like UML did not--or could not--exist.__________________________________________Object Constraint Language:

OCL is a formal system of semantics which is used for establishing the correctness of a "statement" in a programming language. As the name implies, it may constrain an object, by excluding certain types of statements.

Pollice: For example, it could help you indicate that, to be assigned a room, a specific course must have at least six students enrolled. With OCL you could annotate the association between the Course and Classroom classes to represent the constraint, as shown in Figure 1. As an alternative to the note shown in this figure, you could use a constraint connector between the Courseand Classroom classes.

Pollice's article is very enthusiastic about OCL, which is often necessary for an instructor (I usually find I can learn a concept faster if I believe, or convince myself, that the concept is brilliant). He illustrates the difference between a set of semantic rules, which is what OCL is, and an actual language (which would have an explicit syntax and vocabulary). Human languages have surprisingly universal semantics, something that is entirely untrue in either mathematics or programming languages; there, semantic rules vary depending on the logical relationships being manipulated. According to Pollice, OCL has very mathematically-oriented semantics, which makes it especially powerful since mathematics has evolved a very profound, comprehensive semantic structure, whereas programming languages tend to have very rudimentary rules of syntax that are peculiar to each one).

In contrast, many programming languages have semantic rules that are comparatively closer to formal English (e.g., COBOL); this is actually something of a waste for programming objects, an object usually performs a very specific mathematical or logical operation that has no use for the arbitrary and alien constraints of human semantics, which are designed to describe tangible reality. OCL rules for what constitute acceptable language for objects under each objects peculiar conditions and contraints are, things that ought to be applied as understood by the programmer as a tool; the programmer ought not to try to master the entire codex of OCL rules. The benefits of expanding one's knowledge of OCL is that one can learn to think formally, thereby expanding one's power to discern appropriate design approaches.

Needless to say, for anything as influential as UML has been, there are criticisms; what's surprising is how mild they are. For the most part, these consist of inadequacies and omissions in the language. Scott W. Ambler laments that UML is a long way off from true computer-aided software engineering (CASE), and developers are still obligated to develop proprietary extensions to it in order to generate executable code or derive UML models from existing code.

Another criticism is the proliferation of diagrams; while several new ones have been added for UML 2.0, it seems that the large number reflects the sort of committee-induced compromise between incompatible design approaches: include the tools to do both.

This complaint also arises with the logic. UML authorizes the use of OCL semantics, English (detailed semantics) and its own peculiar set, there's an argument that the varied semantic structures defeat the purpose of any. It's unclear if this is necessarily a flaw, though, since different objects may require different semantic structures.__________________________________________NOTES:Complex licensing agreements: frequently an application published for any particular market has many features that any one user is unlikely to use. Plug-ins may well be an option, but in cases where they are not, there is a problem of pricing licenses for proprietary software objects when the developer of the main program expects only 10% or so of users to ever use the feature.

10 October 2006

Hacking

The term "hacking" is often used to refer to the act of editing or fixing flawed computer code. Typically a hack is interpreted as a patch or clever work-around. I have also seen the term used to refer to the creation of forks of computer programs; this latter sense means, the programmer (legally or not) edits the source code of a program so its functionality is different. The programmer then circulates this new, edited version under a new name.

In many cases, a computer programmer requires a specialized program to do this; for example, there are a lot of programs that are used to automatically generate HTML, JavaScript applets, and other quasi-programs. Often they have unsatisfactory quirks, and programmers create programs to follow them around and clean up (or hack) the script. So programs and bots can be surrogate hackers too.

However, it is also the case that "a hack" was often slack at MIT for a prank. Usually hacks (in this sense) were very elaborate pranks that required an immense amount of work.

Another sense of the term "hack" derives from the older jargon, crack. The term "safe cracker" is perhaps well-known to avid readers of pulp fiction; it refers to the trick of opening a safe by manipulating the locking mechanism, rather than blowing it up. Likewise, a "code cracker" was someone who specialized in finding patterns in encrypted data, and thereby decoding it. Applied to computer terminology, it naturally referred to the ability of specialists to defeat or cripple a computer system. One obvious motive for doing this would be crime: a cracker could, for example, crack the security of a bank and change his account balance to whatever he thought he could get away with. Or he could vandalize the system of an organization he loathed.

This has unfortunately created a certain confusion of terms. One of the things any hacker could naturally do quite well is create malware, such as spam bots. Spam bots could conceivably be useful; it's just that they aren't. So the term "hacker" came to be associated with negative, destructive use of skills that are intrinsically valuable.

Richard Stallman introduces a third, closely related, sense of the term hack: the introduction of a novel, potentially useful or entertaining idea. His example includes the trick of eating with more than two chopsticks in one's hand. While this is not very useful, he mentioned that a friend was able to eat with four in his right hand, using them as two pair. It appeals to a sense of playfulness and appreciation for originality.

05 October 2006

Open Source

This is a term of art used to refer to software whose code is available for free public distribution. Of course, "open source" may refer to other types of products, but in computer parlance it implies that that intellectual property rights are greatly restricted. The code may be edited and circulated freely, leading to the gradual evolution of software through the contributions of many.

The concept of "Open Source" software is not as immutable or uncontroversial as it might perhaps sound. For example, open source software used to be known as "free software," which implied both the non-pecuniary nature of the software plus its accessibility to editing by users plus a political connotation of freedom from the institutionally structured, command economy of a corporation or government agency. Well, a large volume of software is available "for free" from both; for example, Acrobat Reader is available for free (thereby creating a market for Acrobat Writer); the Army Corps of Engineers circulates lab software for free (mainly through state governments) for reporting environmental lab results. These are, however, designed to remain under the strict control of the developer, so that the software serves its institutional goals.

Another interesting case is the example of IBM, which distributed the source code to its mainframe software for many years. One of these operating systems, VM/MVS, survived long after IBM had withdrawn any sort of support, and became an early prototype of open source software. At that time, software played a comparatively small role in IBM's bottom line, and the company had an interest in helping customers develop applications that could be ported over to other customers.

Acrobat code is not open source, and hence users cannot modify the reader to be a writer; they certainly cannot make it better than the product distributed by Adobe. The software delivered by the Army Corps of Engineers, COELT, is deliberately unpleasant to use; the Army's software developers have no desire to intrude on the market for automated ELIMS.

In the case of user communities receiving "free" assistance from a private sector developer, it's long been observed that the community adds value to the product far in excess of the company's input. The value added to the product is partly captured by the firm by moving the demand curve for its products to the right, and the rest of the economy benefits from this increment in factor productivity. But this is not, in and of itself, the point of the free software movement. ________________________________________________When I first became aware of the existence of free software, it didn't seem terribly interesting to me because it seemed hopelessly idealistic. Sure, I could understand the desire for a college professor, grad student, hobbyist, or corporate employee to circulate her work for general use; what seemed implausible was the idea that the software would work for very long. For example, I was particularly amazed by the survival of native Unix applications, such as Emacs. How could a program survive if everyone could edit it?

Well, the short answer is that typically software must mesh with other systems whose future evolution is unknown. I could conceivably download GNU Emacs, for example, and edit it as much as I liked. By the end of the year I would have something I call JRM Emacs (i.e., a fork). My fork would still have to be compatible with the Unix API or else it would just sit there useless on the hard drive. On the other hand, it would also have to be able to save files that could be opened by other editions of Emacs--otherwise, it would just be a random heap of symbols, not a program. In order for a schism to appear in the Emacs world, in which two anti-Emacs with incompatible formats limp along with too many users for either to vanish, it would actually be necessary for one of two conditions to prevail:

Either there is some very compelling thing my Emacs does, that all the others don't do;

Or else I and a bunch of other folk went off into some isolated place for a long time, and not only re-wrote Emacs, but also the Unix API's, the libraries, a compiler or two, and several of the other programs that Emacs needs to work with

Should neither of these things happen, then my JRM Emacs has got to solve the problem of doing something better, while at the same time being compatible with all of the rest of the Unix community (that it was compatible with before, I mean). In which case, my JRM Emacs is probably going to be a plug-in, not an entirely new software, and no real schism is likely to appear.

Now, readers familiar with the "Unix Wars" may know the split between Bell Lab's System V and BSD was occasioned by the need to develop a version of Unix that used none of the original AT&T source code. As long as there was some trace of the AT&T programming in it, AT&T had a legal claim on the source code. BSD had initially incorporated much of this source code, and its developers had to effectively re-invent the wheel, so that the new wheel was in fact entirely "free." The importance of this accomplishment I shall explain in a moment.

Another important case is the "Browser War," which was really a sort of ambush and massacre, not a real war. The first common web browser was Netscape Navigator, a semi-free software that gained near-universal acceptance in the mid-1990's. At that time, Microsoft had won a monopoly of system & application software for the consumer PC market, and was mildly concerned about the possibility of competition from the Java platform. It had a browser of its own, MS Internet Explorer (MSIE), which was not catching on because it was an almost supernaturally bad browser. Microsoft started off by giving away the browser for free, then integrated it with MS Windows. There was some inconsequential anti-trust action, but most of this occurred after MSIE had driven Netscape Navigator [mostly] out of the market.

MSIE had won a monopoly on a product by reducing its price to nothing. IE was to prove unusually vulnerable to malware, and MS sat on its victory for six years with no innovation whatever. MS introduced non-standard HTML components, then web-authoring tools that excluded rival browsers (Note: MS Expression and Adobe Dreamweaver appear to have stopped this practice). A large number of fairly important websites effectively bar visitors with non-MSIE browsers, sometimes with cruel consequences.

Now, in the first case, the post-1991 BSD Unix did indeed do something prior versions of Unix did not: it was wholly open source software, which allowed huge numbers of grad students, hobbyists, desperate startups, and so forth to further develop. FreeBSD, OpenBSD, and NetBSD are actually "Unix-like," since they don't actually have permission to characterize themselves as Unix. But the development community is out there adapting to the new technologies available, and fixing bugs much faster than was the case during the years of bondage to AT&T.

In the second case, the division came about because Microsoft is so huge that it could make MSIE recognize nonstandard HTML variants, make Frontpage author those nonstandard HTML variants, promote nonstandard versions of Perl and Javascript (or "Jscript"), and incorporate non-standard elements in the web authoring features of MS Office applications. Please note the different theme in these two examples.________________________________________________In his essay, "The Cathedral and the Bazaar," Unix guru Eric Raymond outlines two basic models of software development communities. One is the cathedral, in which a group of specialists craft standards, and then release those standards at widely-spaced intervals so that the hacking community can then implement them and develop plug-ins. The other is the bazaar, in which there is absolutely no centralizing authority.

Linux overturned much of what I thought I knew. I had been preaching the Unix gospel of small tools, rapid prototyping and evolutionary programming for years. But I also believed there was a certain critical complexity above which a more centralized, a priori approach was required. I believed that the most important software (operating systems and really large tools like the Emacs programming editor) needed to be built like cathedrals, carefully crafted by individual wizards or small bands of mages working in splendid isolation, with no beta to be released before its time.

Linus Torvalds's style of development—release early and often, delegate everything you can, be open to the point of promiscuity—came as a surprise. No quiet, reverent cathedral-building here—rather, the Linux community seemed to resemble a great babbling bazaar of differing agendas and approaches (aptly symbolized by the Linux archive sites, who'd take submissions from anyone) out of which a coherent and stable system could seemingly emerge only by a succession of miracles.

The fact that this bazaar style seemed to work, and work well, came as a distinct shock. As I learned my way around, I worked hard not just at individual projects, but also at trying to understand why the Linux world not only didn't fly apart in confusion but seemed to go from strength to strength at a speed barely imaginable to cathedral-builders.

Raymond's book is influential partly because he is a veteran of so many important open-source software initiatives, such as BSD Unix, and partly because it is actually fairly rare for a technological trend to be interpreted as part of a larger social event (in a reasonably plausible way). Also, Raymond is a talented writer.

A few economists had noticed analogous trends in the past. It was a source of considerable interest to them that highly decentralized groups could organize the planning of future needs and prices more successfully than, say, a benevolent dictator.

As every individual, therefore, endeavours as much as he can both to employ his capital in the support of domestic industry, and so to direct that industry that its produce may be of the greatest value; every individual necessarily labours to render the annual revenue of the society as great as he can. He generally, indeed, neither intends to promote the public interest, nor knows how much he is promoting it. By preferring the support of domestic to that of foreign industry, he intends only his own security; and by directing that industry in such a manner as its produce may be of the greatest value, he intends only his own gain, and he is in this, as in many other cases, led by an invisible hand to promote an end which was no part of his intention. Wealth of Nations, IV.2.9, Adam Smith

Interestingly enough, a close reading of Smith (particularly in the light of his other great work, The Theory of Moral Sentiments) suggests that his intent was closer to Raymond's surprise dicovery, than the intersecting supply and demand curves attributed to it by classical economists who followed. Smith was interested in the idea of the individual guided by the point of view of an imaginary impartial observer, the "man in the glass." He had also noticed a tendency for humans to use the signals from each other to anticipate and adjust to maintain normality.

However, Smith devoted his work to the direct ways in which individual prudence maintained public balance. Left unresolved was the question of individual providentiality towards the commons, and how that created, or preserved commons. The notion of a true commons is one of the great mysteries of classical liberalism. Usually, when people think of a commons, they are thinking of something like a park or the system of freeways--a thing used in common, benefiting all, allowing free riders, and making exclusion of use difficult. However, the most famous examples are poor ones. They aren't commons so much as owned by a large institution that then collects "protection money." One economist, Ronald Coase, famously argued that the commons could and often was protected without a government "owner." In this case, we are talking about a true commons--something for which there is no owner-protector. We are talking about the creative commons, the commons of intellectual accomplishment.

This leads to the fairly interesting paradox of two admirers of Ayn Rand, Raymond and Rideau, with diametrically opposed ideas about the question of intellectual property rights. Raymond perceives intellectual property rights as an indispensable part of free enterprise; Rideau, as a tool for turning corporations and individuals into state surrogates (as enforcers of monopolies). Rideau, arguably, has assimilated Coase's Theorem and recognizes intellectual accomplishment as a form of commons; Raymond perceives Coase's Theorem as not terribly relevant, and intellectual labor as requiring a sort of accumulated property in order for the market to work. Observing as he does that the creative commons (or "ergosphere") flourishes without property rights, he unwittingly (?) invokes Veblen's observations about the leisure class.

Gift cultures are adaptations not to scarcity but to abundance. They arise in populations that do not have significant material-scarcity problems with survival goods. We can observe gift cultures in action among aboriginal cultures living in ecozones with mild climates and abundant food. We can also observe them in certain strata of our own society, especially in show business and among the very wealthy."The Hacker Milieu as Gift Culture"

[...]

In these psychological observations we can ground a case that an open-source development group will be substantially more productive (especially over the long term, in which creativity becomes more critical as a productivity multiplier) than an equivalently sized and skilled group of closed-source programmers (de)motivated by scarcity rewards.

This suggests from a slightly different angle one of the speculations in The Cathedral And The Bazaar; that, ultimately, the industrial/factory mode of software production was doomed to be outcompeted from the moment capitalism began to create enough of a wealth surplus that many programmers could live in a post-scarcity gift culture."Gift Outcompetes Exchange"

I now return to my cases of MSIE creating a standards schism by being able to alter the standards en bloc, like a perverse cathedral; and of the Unix schism created by a standard that was uniquely competent (in this case, capable of being open source). The latter case could only accomplish anything if it established the conditions of the bazaar, in which the ability of people to introduce innovations and improvements became universal.

At this point, I've run out of things to say; there's a ton of more valuable information, including on Wikipedia, available in the linked sites. I haven't finished reading Ko Kuwabara's and Forrest Cavalier's papers, both of which look really good. However, I want to include two disclaimers here before I sign out: first, I am merely studying this topic out of personal interest, and readers ought to know I'm not an expert; and second, like Sir Thomas More in A Man for all Seasons, I have kept silent on how I feel about the actual topic under discussion. What I have done is put forward what I believe is a body of pertinent positions on open source software, and you don't need to know what my opinion of them is.________________________________________________NOTE:ELIMS: electronic laboratory information management system; used to collect data about lab samples, from sample log-in, to extraction, to analysis, to the lab report, thence to archiving or electronic transmission.________________________________________________ADDITIONAL NOTES & READING: The Cathedral & the Bazaar, Eric Raymond, O'Reilly Press (1998); "Some Implications of Bazaar Size," Forrest J. Cavalier, III, 1998; "The Cathedral Cleric and the Bazaar Preacher," Faré Rideau; "Linux: a Bazaar at the Edge of Chaos," Ko Kuwabara

Application Programming Interface (API)

A very important distinguishing feature among operating systems is the application programming interface (API). Essentially, the API is the set of system calls that relays instructions from the software application to the operating system (OS) kernel. In order for an application, such as MS Word or Adobe Acrobat, to run on a computer it is necessary for that version of the application to transmit its system needs in the language used by the operating system. The generic term of art for that common vocabulary is "API."

An API consists of a vocabulary of system calls, or basic instructions/requests for memory, processing capacity, and so on. The kernel responds to these instructions by attempting to allocate system resources to the program. Each system call is likely to correspond to a small piece of programming code, known as an internal. In the conventional concept of an API, each system call corresponds to one of the following:

function or subroutine;

procedure;

variable;

data structure;

Function/Subroutine: this is essentially a portion of programming code that executes a discrete step, such as pushing downward a set of values stored in a memory register; both subroutines and procedures exist in computer programs as well as in kernel system call sets.

Procedure: a set of related control statements that cause one or more programs to be performed [*]. A fairly important type of API procedure is the remote procedure call (RPC), in which a client requests access to system resources located on a different machine.Variable: closely analogous to mathematical variables; in the execution of a program, however, the API needs to associate variables with a corresponding numerical value as value inputs change. As the variable's provisional numerical value changes, the variable must be recorded as having its new value. The value of the variable may take different formats, which are communicated to the kernel with sigils, i.e., symbols that specify the data type. Variables are typically scalar (i.e., countable numerals), alphanumeric, or floating point.

Data Structure: the mode by which the data is organized for computing efficiency. Typically, a good API will recognize just enough basic systems of organizing data for every occasion, but not so many as to allow redundancy. If there are not enough data structures recognized, certain programs that employ them will not operate as efficiently, while too many will increase the number of internals needlessly, thereby making the kernel excessively large. The basic forms of data structure include queue, stack, linked list, heap, dictionary, and tree.The API paradigms above are usually used in the context of an OS running on tangible hardware. (Sorry, I realize that has got to be the most tautological sentence I've typed since graduating from high school!) In some cases, however, an OS may be running on a virtual machine. An example of this is JavaScript, which runs on an interpreter so that programmers aren't required to know how JavaScript API's relate to lower levels of abstraction [*].RESOURCES: Wikipedia entry--see also subroutine, variable, and data structure; "Application Programming Interface,"Software Engineering Institute, Carnegie Mellon Univ.; "Unix for Web developers," eXtropia tutorials [12]; Dictionary of Algorithms and Data Structures;