changeset 12466:b22565172b9b

(Fsafe_length): New function. (syms_of_fns): defsubr it.
author Richard M. Stallman <rms@gnu.org>
date Sat, 01 Jul 1995 22:27:40 +0000
parents 0d404ef125ea
children 01a0910f1987
files src/fns.c
diffstat 1 files changed, 33 insertions(+), 0 deletions(-) [+]
line wrap: on
line diff
--- a/src/fns.c	Sat Jul 01 21:48:13 1995 +0000
+++ b/src/fns.c	Sat Jul 01 22:27:40 1995 +0000
@@ -128,6 +128,38 @@
   return val;
 }
 
+/* This does not check for quits.  That is safe
+   since it must terminate.  */
+
+DEFUN ("safe-length", Fsafe_length, Ssafe_length, 1, 1, 0,
+  "Return the length of a list, but avoid error or infinite loop.\n\
+This function never gets an error.  If LIST is not really a list,\n\
+it returns 0.  If LIST is circular, it returns a finite value\n\
+which is at least the number of distinct elements.")
+ (list)
+     Lisp_Object list;
+{
+  Lisp_Object tail, halftail, length;
+  int len = 0;
+
+  /* halftail is used to detect circular lists.  */
+  halftail = list;
+  for (tail = list; CONSP (tail); tail = XCONS (tail)->cdr)
+    {
+      if (EQ (tail, halftail) && len != 0)
+	{
+	  len /= 2;
+	  break;
+	}
+      len++;
+      if (len & 1 == 0)
+	halftail = XCONS (halftail)->cdr;
+    }
+
+  XSETINT (length, len);
+  return length;
+}
+
 DEFUN ("string-equal", Fstring_equal, Sstring_equal, 2, 2, 0,
   "T if two strings have identical contents.\n\
 Case is significant, but text properties are ignored.\n\
@@ -1512,6 +1544,7 @@
   defsubr (&Sidentity);
   defsubr (&Srandom);
   defsubr (&Slength);
+  defsubr (&Ssafe_length);
   defsubr (&Sstring_equal);
   defsubr (&Sstring_lessp);
   defsubr (&Sappend);