Python 2.7 在python中,如何递归替换字符串中的%占位符

Python 2.7 在python中,如何递归替换字符串中的%占位符,python-2.7,Python 2.7,我有一大块python代码用于构建SQL查询。它通过调用其他几个函数来获取部分查询,然后组装它们来实现这一点。我试图找出如何输出一个字符串,这个字符串就是实际运行的MySQL查询 我不想展示所有的实际代码(因为有很多),而且我对python也不是很了解,但下面是我尝试展示这些代码的功能: import random def myClause(): if (random.randint(1,101) > 50): clause_part = 10; else cla

我有一大块python代码用于构建SQL查询。它通过调用其他几个函数来获取部分查询,然后组装它们来实现这一点。我试图找出如何输出一个字符串,这个字符串就是实际运行的MySQL查询

我不想展示所有的实际代码(因为有很多),而且我对python也不是很了解,但下面是我尝试展示这些代码的功能:

import random

def myClause():
  if (random.randint(1,101) > 50):
    clause_part = 10;
  else
    clause_part = 500;
  clause = "WHERE table2.id > %(clause_part)s
  return clause

def doQuery():
  clause = myClause();
  if (random.randint(1,101) > 50):
    other_clause_part = 10;
  else
    other_clause_part = 500;
  my_sql = """SELECT * FROM table1 JOIN table2 ON table1.t2_id = table2.id
     WHERE table1.id > %(other_clause_part)s
     %(clause)s""" % {'other_clause_part': other_clause_part,
                      'clause': clause}

  print(my_sql)
  cur.execute(my_sql)

它是这样的(是的,我知道,我确信这段代码中有一些python bug,同样,我不知道python)。发生的事情是,当我看到打印出来的结果时,它只计算“other_clause_part”,而不计算“clause”。我猜想这是因为被替换的占位符只深入一层。换句话说,我有占位符,我也有占位符,它们本身也有占位符。有没有什么方法可以递归地替换字符串中的所有占位符,然后在某个地方打印输出?

因此,首先我必须学习更多的python,并使我的示例真正起作用。这使我得出以下结论:

import random

def myClause():
  if (random.randint(1,101) > 50):
    clause_part = 10
  else:
    clause_part = 500
  clause = "WHERE table2.id > %(clause_part)s"
  return clause

def doQuery():
  clause = myClause()
  if (random.randint(1,101) > 50):
    other_clause_part = 10
  else:
    other_clause_part = 500
  my_sql = """SELECT * FROM table1 JOIN table2 ON table1.t2_id = table2.id
    WHERE table1.id > 1 %(other_clause_part)s
    %(clause)s""" % {'other_clause_part': other_clause_part,
                     'clause': clause}

  my_sql2 = my_sql % {'clause_part': 'whatever'}

  print(my_sql2)

doQuery()
我最初尝试做的事情是不可能的,因为第一个字符串中的占位符被另一个占位符替换了。另外,第二个字符串的占位符不在用于替换占位符的数据对象中。(很抱歉,这听起来不对,所以我将举例说明)第一次替换后,我的字符串如下所示:

SELECT * FROM table1 JOIN table2 ON table1.t2_id = table2.id
    WHERE table1.id > 1 500
    WHERE table2.id > %(clause_part)s
现在,如果你看看这个,你会发现在doQuery函数中,我从未定义过“子句\部分”。这是在myClause函数中定义的,但在返回值之前,从未实际应用于字符串作为替换

然后作为一个测试,我加入了另一个替换字符串(“whatever”),现在我可以看到,如果你有某种元组数组,你可以创建一个循环或诸如此类的东西,然后“递归地”替换所有的元组

另一方面,如果您只是想解决我面临的原始实际问题(即试图弄清楚查询到底是什么样子的),您可以改为:

print(cur._last_executed)

对不起,浪费了你所有的时间。也许有人会觉得这很有帮助。

如果您只是在寻找
printf
功能,例如
%s%s”(“一”、“二”)==“一、二”
,但在本例中这不是已经完成了吗?语法很重要。更正字符串格式以匹配预期语法后,您将看到替换。我不认为递归是你问题的一部分,除非我严重误解了你的问题。@Two Bitalchest我完全同意。不幸的是,这是一些我没有编写的过时的10年代码库。如果由我决定的话,我会扔掉这堆废话,用Laravel和雄辩的语言用PHP重写它。尽管如此,考虑到我必须修复它的时间,这对我来说不是一个选项。现在我更仔细地阅读了你的问题-
子句
也是一个格式字符串。也就是说,它正在进行替换,但是被替换的值包含其他格式占位符。从你的问题来看,至少对我来说,还不清楚应该用什么来取代这些东西。我不认为你在浪费任何人的时间。谢谢你的自我回答。我相信你很快就能接受自己的答案。你会惊讶地发现,像这样的简单问题会有帮助!不管怎样,很高兴我似乎把你推向了正确的方向。你可能还想看看关于
str.format
的更多信息。它比以前的
%
格式更适合您正在进行的命名替换。如果折衷值得重写,则由您决定。干杯为了便于学习,我会检查一下。由于这不是我的代码,我的目标是尽可能少地修改它。我在这里的唯一目标是优化查询。再次感谢。