summaryrefslogtreecommitdiffstats
path: root/tcllib/modules/tie/tie_array.tcl
blob: 5267970118c20f677e5b569bdfece7d0b3b7d4df (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
# tie_array.tcl --
#
#	Data source: Tcl array.
#
# Copyright (c) 2004 Andreas Kupries <andreas_kupries@users.sourceforge.net>
#
# See the file "license.terms" for information on usage and redistribution
# of this file, and for a DISCLAIMER OF ALL WARRANTIES.
# 
# RCS: @(#) $Id: tie_array.tcl,v 1.3 2005/09/28 04:51:24 andreas_kupries Exp $

# ### ### ### ######### ######### #########
## Requisites

package require snit
package require tie

# ### ### ### ######### ######### #########
## Implementation

snit::type ::tie::std::array {

    # ### ### ### ######### ######### #########
    ## Specials

    pragma -hastypemethods no
    pragma -hasinfo        no
    pragma -simpledispatch yes

    # ### ### ### ######### ######### #########
    ## API : Construction & Destruction

    constructor {rvar} {
	# Bring reference to the array into the object scope,
	# i.e. namespace of the object. This will fail for proc local
	# variables. This latter is enforced by the core, to prevent
	# the existence of dangling references to the variable when
	# the procedure goes away.

	# upvar 3, because we have to skip 3 snit internal levels to
	# access the callers level.

	if {[catch {
	    upvar 3 $rvar ${selfns}::thesource
	}]} {
	    return -code error "Illegal use of proc local array variable \"$rvar\""
	}

	# Now bring the variable into method scope as well, to check
	# for its existence.

	variable ${selfns}::thesource

	if {![array exists thesource]} {
	    return -code error "Undefined source array variable \"$rvar\""
	}
	return
    }

    # ### ### ### ######### ######### #########
    ## API : Data source methods

    method get {} {
	variable ${selfns}::thesource
	return [array get thesource]
    }

    method set {dict} {
	variable ${selfns}::thesource
	return [array set thesource $dict]
    }

    method unset {{pattern *}} {
	variable ${selfns}::thesource
	array unset thesource $pattern
	return
    }

    method names {} {
	variable ${selfns}::thesource
	return [array names thesource]
    }

    method size {} {
	variable ${selfns}::thesource
	return [array size thesource]
    }

    method getv {index} {
	variable ${selfns}::thesource
	return $thesource($index)
    }

    method setv {index value} {
	variable ${selfns}::thesource
	set thesource($index) $value
	return
    }

    method unsetv {index} {
	variable ${selfns}::thesource
	unset thesource($index)
	return
    }

    # ### ### ### ######### ######### #########
    ## Internal : Instance data

    ## During construction the source array variable is imported into
    ## the namespace of the object, for direct access through a
    ## constant name. This also allows a direct reference without
    ## having to deal with changing stack scopes. This is possible if
    ## and only if the imported array is a namespaced variable. Proc
    ## local variables cannot be imported into a namespace in this
    ## manner. Trying to do so results in an error.

    # ### ### ### ######### ######### #########
}

# ### ### ### ######### ######### #########
## Ready to go

::tie::register ::tie::std::array as array
package provide   tie::std::array 1.0