def _get_OriginInfo_map(self): # step1 dygraph_ast = gast.parse(self.source_code) dygraph_ast = attach_origin_info(dygraph_ast, self.dygraph_func) # step2 transformed_ast = DygraphToStaticAst().get_static_ast(dygraph_ast).node # step3 self.static_func, _ = ast_to_func(transformed_ast, self.dygraph_func) info_map = create_and_update_origin_info_map(dygraph_ast, self.static_func) return info_map
def convert_to_static(dyfunc): """ Converts dygraph function into static function. """ # Get AST from dygraph function raw_code = inspect.getsource(dyfunc) code = textwrap.dedent(raw_code) root = gast.parse(code) # Transform AST dygraph_to_static = DygraphToStaticAst() root_wrapper = dygraph_to_static.get_static_ast(root) # Get static_func from AST static_func, file_name = ast_to_func(root_wrapper.node, dyfunc) return static_func, dygraph_to_static
def convert_to_static(dyfunc): """ Converts dygraph function into static function. """ # Get AST from dygraph function # Note: In Python2, it will raise OSError when inspect function # with decorator directly and dyfunc.__wrapped__ holds the actual function. dyfunc = getattr(dyfunc, '__wrapped__', dyfunc) raw_code = inspect.getsource(dyfunc) code = textwrap.dedent(raw_code) root = gast.parse(code) # Transform AST dygraph_to_static = DygraphToStaticAst() root_wrapper = dygraph_to_static.get_static_ast(root) # Get static_func from AST static_func, file_name = ast_to_func(root_wrapper.node, dyfunc) return static_func, dygraph_to_static
def _convert(self, func): """ Converts dygraph function into static function. For two functions with same dedent code, the second function will reuse the transformed ast node of previous one. For example: # A.py def foo(x, y): z = x + y return z # B.py def foo(x, y): z = x + y return z If the conversion of A.foo happens after B.foo, it will reuse the transformed ast node of B.foo to speed up the conversion. """ # Note: In Python2, it will raise OSError when inspect function # with decorator directly and function.__wrapped__ holds the actual function. func = unwrap(func) source_code = func_to_source_code(func) # TODO(liym27): # Consider this case: source_code in self._code_to_ast_caches, # but actually they are methods in different classes. # Maybe use (__class__, source_code) as key if source_code in self._code_to_ast_caches: root_wrapper = self._code_to_ast_caches[source_code] else: root = gast.parse(source_code) root = attach_origin_info(root, func) root_wrapper = self._dygraph_to_static.get_static_ast(root) self._code_to_ast_caches[source_code] = root_wrapper # Get static function from AST static_func, file_name = ast_to_func(root_wrapper.node, func) create_and_update_origin_info_map(root_wrapper.node, static_func) return static_func
def test_ast2func_error(self): with self.assertRaises(Exception) as e: self.assertRaises(TypeError, ast_to_func("x = a + b", 'foo')) self.assertTrue("Type of ast_root should be gast.AST or ast.AST" in str(e.exception))
def _ast2func(self, func): source = inspect.getsource(func) source = textwrap.dedent(source) ast_root = gast.parse(source) transformed_func, _ = ast_to_func(ast_root, func) return transformed_func