CMP EMBEDDED.COM

Login | Register     Welcome Guest  
HOME DESIGN PRODUCTS COLUMNS E-LEARNING CONFERENCES CODE FORUMS/BLOGS NEWSLETTERS CONTACT FEATURES RSS RSS

Making the transition from sequential to implicit parallel programming: Part 5
Implicit Parallel Programming: Declarative Programming Languages



Embedded.com
Since dealing with state (reuse of storage) causes so much difficulty for parallel execution, we can ask if there are programming notations that avoid the notion of state completely, and whether such notations are adequate for general-purpose programming.

The answer to the first question is yes - such languages are called declarative languages - but the answer to the second question is no - some programming tasks are difficult, if not impossible, to express declaratively.

The efficient implementation of pure declarative languages is also very difficult (curiously, the implementation problem is the dual of the automatic parallelization problem, an observation that we will return to shortly). Nevertheless, declarative languages are an excellent basis for more complete parallel programming languages and, indeed pH, the language advocated in this series of articles, is based on this idea.

A well-known class of declarative languages is that of functional programming languages, such as Lisp, SML and Haskell [26]. Hughes provides an excellent articulation of the advantages of functional programming in "Why Functional Programming Matters" [18]. A second well-known class is that of logic programming languages, such as Prolog  and KL1 and their more modern derivatives, constraint logic programming languages, such as Oz . We will mainly discuss functional languages here (because of their relationship to pH), but many of our remarks also apply to the latter.

As an aside, we note that the adjective "declarative" is subjective. Intuitively it means that the program describes what is to be computed rather than how to compute it. Such a description is "higher level", or more "abstract" and hence presumably easier for humans to write and comprehend.

However, no programming language can ever get away completely from the how of problem solving. The most abstract descriptions of computations may not even be executable (such descriptions are the purest form of specifications).

For example, an abstract description of the square root function is "the function which, for argument n, produces x such that x2 = n." An abstract description of a sorting function is "the function which, for argument sequence xs, produces the sequence ys which is a permutation of xs and in which y(i) < y(i+l)."

It is unreasonable to expect any interpreter/compiler to actually execute these specifications systematically and efficiently. Thus, all programming, no matter how high level, fundamentally concerns algorithms, which specify how to compute an answer. So, the adjective "declarative" is mainly an assessment of how much non-problem-specific detail can be suppressed in a programming language.

At one extreme (least declarative) is architecture-specific assembler, where the programmer is intimately concerned with managing storage layout, movement of data between registers and memory, and sequencing.

Most architecture-independent programming languages such as C, Pascal, and Fortran abstract away from some storage-layout details and provide higher-level control structures such as if-then-elses, loops, and recursive procedures.

Some object oriented languages like Java provide even higher-level structures such as data abstraction and inheritance and further relieve the programmer from storage-management details by managing storage deallocation automatically.

Declarative languages like functional and logic programming languages abstract away from storage layout and storage management details completely and also abstract away from many sequencing details.

1 | 2 | 3

Rate this article: Low High
Current rating
  • .
Embedded.com Career Center
Looking for a new job?
SEARCH JOBS

Browse all jobs

SPONSOR
RECENT JOB POSTINGS





 :