From octave-maintainers-request at bevo dot che dot wisc dot edu Fri Nov 22 15:44:40 2002 Subject: Re: Are functional objects (functors/closures) possible? From: "John W. Eaton" To: Paul Kienzle Cc: octave-maintainers mailing list Date: Fri, 22 Nov 2002 15:44:37 -0600 In a message to the help-octave mailing list on 22-Nov-2002, Paul Kienzle wrote: | This is a little cleaner if curry were a text function: | | f = curry x y "g(x,y,$a,$b)" | | but right now you cannot tag a function as a text function | unless it is a built-in. How about the following patch, relative to the current CVS? With it, Octave behaves like this: octave:1> mark_as_text_function doit octave:2> function doit (a, b, c) printf ("%s:%s:%s\n", a, b, c); end octave:3> doit foo bar baz foo:bar:baz octave:4> unmark_text_function doit octave:5> doit foo bar baz parse error: >>> doit foo bar baz ^ octave:5> doit ("foo", "bar", "baz") foo:bar:baz octave:6> mark_as_text_function doit octave:7> doit ("foo", "bar", "baz") foo:bar:baz So you could set up a collection of text functions either in a script file or just by marking them in your ~/.octaverc file. I think this is all that is required, but perhaps I'm missing something? If you already submitted a patch like this and I'm reinventing something, then I apologize for that. I didn't try to locate it because it seemed simple enough to implement. Note that these changes require the STL std::set template, which works best with g++ 3.2, at least for me (see my previous post). jwe src/ChangeLog: 2002-11-22 John W. Eaton * variables.cc (text_function_set): New static data. (mark_as_text_function, unmark_text_function, is_marked_as_text_function, Fmark_as_text_function, Funmark_text_function): New functions. (is_text_function_name): Handle functions marked as text functions in special list, not just those marked in the symbol record. * symtab.h (symbol_record::mark_as_text_function, symbol_record::unmark_text_function, symbol_record::symbol_def::mark_as_text_function, symbol_record::symbol_def::unmark_text_function): New functions. Index: src/symtab.h =================================================================== RCS file: /usr/local/cvsroot/octave/src/symtab.h,v retrieving revision 1.60 diff -u -r1.60 symtab.h --- src/symtab.h 20 Nov 2002 16:56:49 -0000 1.60 +++ src/symtab.h 22 Nov 2002 21:38:06 -0000 at @ -106,6 +106,12 @@ bool is_user_variable (void) const { return (symbol_type & symbol_record::USER_VARIABLE); } + void mark_as_text_function (void) + { symbol_type |= symbol_record::TEXT_FUNCTION; } + + void unmark_text_function (void) + { symbol_type &= ~symbol_record::TEXT_FUNCTION; } + bool is_text_function (void) const { return (symbol_type & symbol_record::TEXT_FUNCTION); } at @ -236,6 +242,12 @@ bool is_function (void) const { return definition->is_function (); } + + void mark_as_text_function (void) + { definition->mark_as_text_function (); } + + void unmark_text_function (void) + { definition->unmark_text_function (); } bool is_text_function (void) const { return definition->is_text_function (); } Index: src/variables.cc =================================================================== RCS file: /usr/local/cvsroot/octave/src/variables.cc,v retrieving revision 1.234 diff -u -r1.234 variables.cc --- src/variables.cc 14 Nov 2002 04:31:19 -0000 1.234 +++ src/variables.cc 22 Nov 2002 21:38:07 -0000 at @ -27,6 +27,7 @@ #include #include +#include #include #include "file-stat.h" at @ -103,11 +104,108 @@ // Is this a text-style function? +static std::set text_function_set; + +static inline bool +is_marked_as_text_function (const std::string& s) +{ + return text_function_set.find (s) != text_function_set.end (); +} + +static inline void +mark_as_text_function (const std::string& s) +{ + text_function_set.insert (s); +} + +static inline void +unmark_text_function (const std::string& s) +{ + text_function_set.erase (s); + + symbol_record *sr = fbi_sym_tab->lookup (s); + + if (sr) + sr->unmark_text_function (); +} + +DEFUN_TEXT (mark_as_text_function, args, , + "-*- texinfo -*-\n\ + at deftypefn {Built-in Function} {} mark_as_text_function (@var{name})\n\ +Enter at var{name} into the list of text functions\n\ + at end deftypefn") +{ + octave_value_list retval; + + int nargin = args.length (); + + if (nargin > 0) + { + int argc = nargin + 1; + + string_vector argv = args.make_argv ("mark_as_text_function"); + + if (! error_state) + { + for (int i = 1; i < argc; i++) + mark_as_text_function (argv[i]); + } + } + else + print_usage ("mark_as_text_function"); + + return retval; +} + +DEFUN_TEXT (unmark_text_function, args, , + "-*- texinfo -*-\n\ + at deftypefn {Built-in Function} {} mark_as_text_function (@var{name})\n\ +Enter at var{name} into the list of text functions\n\ + at end deftypefn") +{ + octave_value_list retval; + + int nargin = args.length (); + + if (nargin > 0) + { + int argc = nargin + 1; + + string_vector argv = args.make_argv ("unmark_text_function"); + + if (! error_state) + { + for (int i = 1; i < argc; i++) + unmark_text_function (argv[i]); + } + } + else + print_usage ("unmark_text_function"); + + return retval; +} + bool is_text_function_name (const std::string& s) { + bool retval = false; + symbol_record *sr = fbi_sym_tab->lookup (s); - return (sr && sr->is_text_function ()); + + if (sr) + { + if (sr->is_text_function ()) + retval = true; + else if (is_marked_as_text_function (s)) + { + sr->mark_as_text_function (); + retval = true; + } + } + else + retval = is_marked_as_text_function (s); + + return retval; } // Is this a built-in function?