summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--generic/tclDictObj.c6
-rw-r--r--generic/tclInt.h2
-rw-r--r--generic/tclListObj.c1
-rw-r--r--generic/tclStringObj.c11
4 files changed, 20 insertions, 0 deletions
diff --git a/generic/tclDictObj.c b/generic/tclDictObj.c
index e602c9f..c235d9d 100644
--- a/generic/tclDictObj.c
+++ b/generic/tclDictObj.c
@@ -138,6 +138,8 @@ typedef struct ChainEntry {
*/
typedef struct Dict {
+ int numChars; /* The number of chars in the string. -1 means
+ * this value has not been calculated. */
Tcl_HashTable table; /* Object hash table to store mapping in. */
ChainEntry *entryChainHead; /* Linked list of all entries in the
* dictionary. Used for doing traversal of the
@@ -388,6 +390,7 @@ DupDictInternalRep(
* Initialise other fields.
*/
+ newDict->numChars = -1;
newDict->epoch = 0;
newDict->chain = NULL;
newDict->refcount = 1;
@@ -709,6 +712,7 @@ SetDictFromAny(
*/
TclFreeIntRep(objPtr);
+ dict->numChars = -1;
dict->epoch = 0;
dict->chain = NULL;
dict->refcount = 1;
@@ -1397,6 +1401,7 @@ Tcl_NewDictObj(void)
Tcl_InvalidateStringRep(dictPtr);
dict = ckalloc(sizeof(Dict));
InitChainTable(dict);
+ dict->numChars = -1;
dict->epoch = 0;
dict->chain = NULL;
dict->refcount = 1;
@@ -1446,6 +1451,7 @@ Tcl_DbNewDictObj(
Tcl_InvalidateStringRep(dictPtr);
dict = ckalloc(sizeof(Dict));
InitChainTable(dict);
+ dict->numChars = -1;
dict->epoch = 0;
dict->chain = NULL;
dict->refcount = 1;
diff --git a/generic/tclInt.h b/generic/tclInt.h
index df1507d..74ca252 100644
--- a/generic/tclInt.h
+++ b/generic/tclInt.h
@@ -2406,6 +2406,8 @@ typedef enum TclEolTranslation {
*/
typedef struct List {
+ int numChars; /* The number of chars in the string. -1 means
+ * this value has not been calculated. */
int refCount;
int maxElemCount; /* Total number of element array slots. */
int elemCount; /* Current number of list elements. */
diff --git a/generic/tclListObj.c b/generic/tclListObj.c
index 6cbb10f..bdadaec 100644
--- a/generic/tclListObj.c
+++ b/generic/tclListObj.c
@@ -109,6 +109,7 @@ NewListIntRep(
return NULL;
}
+ listRepPtr->numChars = -1;
listRepPtr->canonicalFlag = 0;
listRepPtr->refCount = 0;
listRepPtr->maxElemCount = objc;
diff --git a/generic/tclStringObj.c b/generic/tclStringObj.c
index 64c661b..040c287 100644
--- a/generic/tclStringObj.c
+++ b/generic/tclStringObj.c
@@ -483,6 +483,17 @@ Tcl_GetCharLength(
return length;
}
+ if ((objPtr->typePtr == &tclDictType)
+ || (objPtr->typePtr == &tclListType)) {
+ List *list = objPtr->internalRep.twoPtrValue.ptr1;
+ if (list->numChars == -1) {
+ (void) TclGetString(objPtr);
+ TclNumUtfChars(numChars, objPtr->bytes, objPtr->length);
+ list->numChars = numChars;
+ }
+ return list->numChars;
+ }
+
/*
* OK, need to work with the object as a string.
*/