empty tuple optimization
authorRobert Bradshaw <robertwb@math.washington.edu>
Thu, 17 Jan 2008 10:08:48 +0000 (02:08 -0800)
committerRobert Bradshaw <robertwb@math.washington.edu>
Thu, 17 Jan 2008 10:08:48 +0000 (02:08 -0800)
Cython/Compiler/ExprNodes.py
Cython/Compiler/ModuleNode.py
Cython/Compiler/Naming.py

index dcf6532bc963df0a291f0e53bcbc6a166b83ccac..f571cc03426ea11db53091c69622504633f8029c 100644 (file)
@@ -2118,6 +2118,19 @@ class SequenceNode(ExprNode):
 
 class TupleNode(SequenceNode):
     #  Tuple constructor.
+    
+    def analyse_types(self, env):
+        if len(self.args) == 0:
+            self.type = py_object_type
+            self.is_temp = 0
+        else:
+            SequenceNode.analyse_types(self, env)
+            
+    def calculate_result_code(self):
+        if len(self.args) > 0:
+            error(pos, "Positive length tuples must be constructed.")
+        else:
+            return Naming.empty_tuple
 
     def compile_time_value(self, denv):
         values = self.compile_time_value_list(denv)
@@ -2127,6 +2140,9 @@ class TupleNode(SequenceNode):
             self.compile_time_value_error(e)
     
     def generate_operation_code(self, code):
+        if len(self.args) == 0:
+            # result_code is Naming.empty_tuple
+            return
         code.putln(
             "%s = PyTuple_New(%s); %s" % (
                 self.result_code,
index c7e4f1fecb4ab8ab3063d6e7a2049401f0f172b6..6deb2f79a64478e72433b98cc23c0ca8667f8103 100644 (file)
@@ -286,6 +286,7 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
         code.putln('')
         code.putln('static PyObject *%s;' % env.module_cname)
         code.putln('static PyObject *%s;' % Naming.builtins_cname)
+        code.putln('static PyObject *%s;' % Naming.empty_tuple)
         if Options.pre_import is not None:
             code.putln('static PyObject *%s;' % Naming.preimport_cname)
         code.putln('static int %s;' % Naming.lineno_cname)
@@ -1271,6 +1272,8 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
         if Options.cache_builtins:
             code.putln("/*--- Builtin init code ---*/")
             self.generate_builtin_init_code(env, code)
+            
+        code.putln("%s = PyTuple_New(0); %s" % (Naming.empty_tuple, code.error_goto_if_null(Naming.empty_tuple, self.pos)));
 
         code.putln("/*--- Global init code ---*/")
         self.generate_global_init_code(env, code)
@@ -1324,6 +1327,7 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
             code.putln("/*--- Builtin cleanup code ---*/")
             for entry in env.cached_builtins:
                 code.put_var_decref_clear(entry)
+        code.putln("Py_DECREF(%s); %s = 0;" % (Naming.empty_tuple, Naming.empty_tuple));
         code.putln("/*--- Intern cleanup code ---*/")
         for entry in env.pynum_entries:
             code.put_var_decref_clear(entry)
index 6ad9ae2a882ee3ae7a62438be261db0f5ed5e674..acdd674f4d26406eebc96886697eb9fec875f286 100644 (file)
@@ -58,6 +58,8 @@ vtabslot_cname   = pyrex_prefix + "vtab"
 c_api_tab_cname  = pyrex_prefix + "c_api_tab"
 gilstate_cname   = pyrex_prefix + "state"
 skip_dispatch_cname = pyrex_prefix + "skip_dispatch"
+empty_tuple      = pyrex_prefix + "empty_tuple"
+
 
 extern_c_macro  = pyrex_prefix.upper() + "EXTERN_C"