Results 1  10
of
17
Functional Programming with Graphs
 2ND ACM SIGPLAN INT. CONF. ON FUNCTIONAL PROGRAMMING
, 1997
"... Graph algorithms expressed in functional languages often suffer from their inherited imperative, statebased style. In particular, this impedes formal program manipulation. We show how to model persistent graphs in functional languages by graph constructors. This provides a decompositional view of g ..."
Abstract

Cited by 34 (13 self)
 Add to MetaCart
Graph algorithms expressed in functional languages often suffer from their inherited imperative, statebased style. In particular, this impedes formal program manipulation. We show how to model persistent graphs in functional languages by graph constructors. This provides a decompositional view of graphs which is very close to that of data types and leads to a "more functional" formulation of graph algorithms. Graph constructors enable the definition of general fold operations for graphs. We present a promotion theorem for one of these folds that allows program fusion and the elimination of intermediate results. Fusion is not restricted to the elimination of treelike structures, and we prove another theorem that facilitates the elimination of intermediate graphs. We describe an MLimplementation of persistent graphs which efficiently supports the presented fold operators. For example, depthfirstsearch expressed by a fold over a functional graph has the same complexity as the corresp...
Inductive Graphs and Functional Graph Algorithms
, 2001
"... We propose a new style of writing graph algorithms in functional languages which is based on an alternative view of graphs as inductively defined data types. We show how this graph model can be implemented efficiently, and then we demonstrate how graph algorithms can be succinctly given by recursive ..."
Abstract

Cited by 25 (2 self)
 Add to MetaCart
We propose a new style of writing graph algorithms in functional languages which is based on an alternative view of graphs as inductively defined data types. We show how this graph model can be implemented efficiently, and then we demonstrate how graph algorithms can be succinctly given by recursive function definitions based on the inductive graph view. We also regard this as a contribution to the teaching of algorithms and data structures in functional languages since we can use the functionalstyle graph algorithms instead of the imperative algorithms that are dominant today. Keywords: Graphs in Functional Languages, Recursive Graph Algorithms, Teaching Graph Algorithms in Functional Languages
Purely Functional RandomAccess Lists
 In Functional Programming Languages and Computer Architecture
, 1995
"... We present a new data structure, called a randomaccess list, that supports array lookup and update operations in O(log n) time, while simultaneously providing O(1) time list operations (cons, head, tail). A closer analysis of the array operations improves the bound to O(minfi; log ng) in the wor ..."
Abstract

Cited by 17 (2 self)
 Add to MetaCart
(Show Context)
We present a new data structure, called a randomaccess list, that supports array lookup and update operations in O(log n) time, while simultaneously providing O(1) time list operations (cons, head, tail). A closer analysis of the array operations improves the bound to O(minfi; log ng) in the worst case and O(log i) in the expected case, where i is the index of the desired element. Empirical evidence suggests that this data structure should be quite efficient in practice. 1 Introduction Lists are the primary data structure in every functional programmer 's toolbox. They are simple, convenient, and usually quite efficient. The main drawback of lists is that accessing the ith element requires O(i) time. In such situations, functional programmers often find themselves longing for the efficient random access of arrays. Unfortunately, arrays can be quite awkward to implement in a functional setting, where previous versions of the array must be available even after an update. Since arra...
RealTime Deques, Multihead Turing Machines, and Purely Functional Programming
 In Conference on Functional Programming Languages and Computer Architecture
, 1993
"... We answer the following question: Can a deque (double ended queue) be implemented in a purely functional language such that each push or pop operation on either end of a queue is accomplished in O(1) time in the worst case? The answer is yes, thus solving a problem posted by Gajewska and Tarjan [1 ..."
Abstract

Cited by 13 (1 self)
 Add to MetaCart
(Show Context)
We answer the following question: Can a deque (double ended queue) be implemented in a purely functional language such that each push or pop operation on either end of a queue is accomplished in O(1) time in the worst case? The answer is yes, thus solving a problem posted by Gajewska and Tarjan [14] and by Ponder, McGeer, and Ng [25], and refining results of Sarnak [26] and Hoogerwoord [18]. We term such a deque realtime, since its constant worstcase behavior might be useful in real time programs (assuming realtime garbage collection [3], etc.) Furthermore, we show that no restriction of the functional language is necessary, and that push and pop operations on previous versions of a deque can also be achieved in constant time. We present a purely functional implementation of real time deques and its complexity analysis. We then show that the implementation has some interesting implications, and can be used to give a realtime simulation of a multihead Turing machine in a purel...
A New Method for Functional Arrays
 Journal of Functional Programming
, 1997
"... Arrays are probably the most widely used data structure in imperative programming languages, yet functional languages typically only support arrays in a limited manner, or prohibit them entirely. This is not too surprising, since most other mutable data structures, such as trees, have elegant immuta ..."
Abstract

Cited by 12 (0 self)
 Add to MetaCart
Arrays are probably the most widely used data structure in imperative programming languages, yet functional languages typically only support arrays in a limited manner, or prohibit them entirely. This is not too surprising, since most other mutable data structures, such as trees, have elegant immutable analogues in the functional world, whereas arrays do not. Previous attempts at addressing the problem have suffered from one of three weaknesses, either that they don't support arrays as a persistent data structure (unlike the functional analogues of other imperative data structures), or that the range of operations is too restrictive to support some common array algorithms efficiently, or that they have performance problems. Our technique provides arrays as a true functional analogue of imperative arrays with the properties that functional programmers have come to expect from their data structures. To efficiently support array algorithms from the imperative world, we provide O(1) operations for singlethreaded array use. Fully persistent array use can also be provided at O(1) amortized cost, provided that the algorithm satisfies a simple requirement as to uniformity of access. For those algorithms which do not access the array uniformly or singlethreadedly, array reads or updates take at most O(log n) amortized time, where n is the size of the array. Experimental results indicate that the overheads of our technique are acceptable in practice for many applications.
Refining FirstClass Stores
 In Proceedings of the ACM SIGPLAN Workshop on State in Programming Languages
, 1993
"... A firstclass store is an object that captures the values of mutable objects at a particular time in a program's execution. Firstclass stores allow programmers to cleanly, safely, and efficiently implement "undo" and "redo" operations on mutable objects. This paper describe ..."
Abstract

Cited by 11 (2 self)
 Add to MetaCart
A firstclass store is an object that captures the values of mutable objects at a particular time in a program's execution. Firstclass stores allow programmers to cleanly, safely, and efficiently implement "undo" and "redo" operations on mutable objects. This paper describes a generalized interface for firstclass stores that allows the programmer to partition mutable data and refine the scope of store objects. We demonstrate the power of the interface by discussing three applications: version arrays, replay debugging, and nested transactions. A denotational semantics for firstclass stores is given and two implementations are discussed. 1 Introduction Firstclass continuations provide programmers with the ability to manipulate the control of their program in many flexible ways. Operationally, we can think of capturing the current continuation as capturing the current program counter and lexical environment of a program and binding it to a variable. Similarly, invoking a continuation...
Fully Persistent Arrays for Efficient Incremental Updates and Voluminous Reads
 4th European Symposium on Programming
, 1992
"... The array update problem in a purely functional language is the following: once an array is updated, both the original array and the newly updated one must be preserved to maintain referential transparency. We devise a very simple, fully persistent data structure to tackle this problem such that ..."
Abstract

Cited by 7 (2 self)
 Add to MetaCart
(Show Context)
The array update problem in a purely functional language is the following: once an array is updated, both the original array and the newly updated one must be preserved to maintain referential transparency. We devise a very simple, fully persistent data structure to tackle this problem such that ffl each incremental update costs O(1) worstcase time, ffl a voluminous sequence of r reads cost in total O(r) amortized time, and ffl the data structure use O(n + u) space, where n is the size of the array and u is the total number of updates. A sequence of r reads is voluminous if r is \Omega\Gamma n) and the sequence of arrays being read forms a path of length O(r) in the version tree. A voluminous sequence of reads may be mixed with updates without affecting either the performance of reads or updates. An immediate consequence of the above result is that if a functional program is singlethreaded, then the data structure provides a simple and efficient implementation of funct...
A Probabilistic Approach to the Problem of Automatic Selection of Data Representations
 In Proceedings of the 1996 ACM SIGPLAN International Conference on Functional Programming
, 1996
"... The design and implementation of efficient aggregate data structures has been an important issue in functional programming. It is not clear how to select a good representation for an aggregate when access patterns to the aggregate are highly variant, or even unpredictable. Previous approaches rely o ..."
Abstract

Cited by 6 (3 self)
 Add to MetaCart
(Show Context)
The design and implementation of efficient aggregate data structures has been an important issue in functional programming. It is not clear how to select a good representation for an aggregate when access patterns to the aggregate are highly variant, or even unpredictable. Previous approaches rely on compiletime analyses or programmer annotations. These methods can be unreliable because they try to predict program behaviors before they are executed. We propose a probabilistic approach, which is based on Markov processes, for automatic selection of data representations. The selection is modeled as a random process moving in a graph with weighted edges. The proposed approach employs coin tossing at runtime to aid choosing suitable data representations. The transition probability function used by the coin tossing is constructed in a simple and common way from a measured cost function. We show that, under this setting, random selection of data representations can be quite effective. Th...
A Randomized Implementation of Multiple Functional Arrays
 In Proceedings of 1994 ACM Conference on Lisp and Functional Programming
, 1994
"... The array update problem in the implementation of a purely functional language is the following: once an array is updated, both the original array and the newly updated one must be preserved to maintain referential transparency. Previous approaches have mainly based on the detection or enforcement o ..."
Abstract

Cited by 5 (1 self)
 Add to MetaCart
(Show Context)
The array update problem in the implementation of a purely functional language is the following: once an array is updated, both the original array and the newly updated one must be preserved to maintain referential transparency. Previous approaches have mainly based on the detection or enforcement of singlethreaded accesses to an aggregate, by means of compilertime analyses or language restrictions. These approaches cannot deal with aggregates which are updated in a multithreaded manner. Baker's shallow binding scheme can be used to implement multithreaded functional arrays. His scheme, however, can be very expensive if there are repeated alternations between long binding paths. We design a scheme that fragments binding paths randomly. The randomization scheme is online, simple to implement, and its expected performance comparable to that of the optimal offline solutions. All this is achieved without using compilertime analyses, and without restricting the languages. The ...
Extending garbage collection to complex data structures
 In SPACE 2006
, 2006
"... Beware lest you lose the substance by grasping at the shadow. —Aesop Objects that are pointer reachable through a complex data structure may be inaccessible to the external program, depending on the semantics of the structure. Failure to recognize the unusual behavior of complex data structures ca ..."
Abstract

Cited by 1 (0 self)
 Add to MetaCart
(Show Context)
Beware lest you lose the substance by grasping at the shadow. —Aesop Objects that are pointer reachable through a complex data structure may be inaccessible to the external program, depending on the semantics of the structure. Failure to recognize the unusual behavior of complex data structures causes memory leaks in any collector that relies on pointer reachability to locate garbage. We extend the definition of reachability to distinguish between objects that are reachable to the program at large and objects that are within the interior of structures. Our general mechanism allows any structure to run arbitrarily complex collection algorithms during normal garbage collection.