簡體   English   中英

使用 AST 匹配器匹配可變參數模板 arguments

[英]Matching variadic template arguments using an AST Matcher

我有以下示例代碼。

template<class T, class... Args>
T add(T first, Args... rest) {
    return first + add(rest...);
}

int add(int a, int b) {
    return a + b;
}

當我通過clang-check -ast-dump運行它時,我得到以下樹。

FunctionDecl 0x4df0b08 <tmp.cpp:2:1, line:4:1> line:2:3 add 'T (T, Args...)'
|-ParmVarDecl 0x4df0928 <col:7, col:9> col:9 referenced first 'T'
|-ParmVarDecl 0x4df09f8 <col:16, col:24> col:24 referenced rest 'Args...' pack
`-CompoundStmt 0x4df0dd0 <col:30, line:4:1>
  `-ReturnStmt 0x4df0dc0 <line:3:5, col:31>
    `-BinaryOperator 0x4df0da0 <col:12, col:31> '<dependent type>' '+'
      |-DeclRefExpr 0x4df0cd0 <col:12> 'T' lvalue ParmVar 0x4df0928 'first' 'T'
      `-CallExpr 0x4df0d78 <col:20, col:31> '<dependent type>'
        |-UnresolvedLookupExpr 0x4df0cf0 <col:20> '<overloaded function type>' lvalue (ADL) = 'add' 0x4df0ba8
        `-PackExpansionExpr 0x4df0d58 <col:24, col:28> '<dependent type>' lvalue
          `-DeclRefExpr 0x4df0d38 <col:24> 'Args' lvalue ParmVar 0x4df09f8 'rest' 'Args...'

FunctionDecl 0x4df0f60 <tmp.cpp:6:1, line:8:1> line:6:5 add 'int (int, int)'
|-ParmVarDecl 0x4df0e00 <col:9, col:13> col:13 used a 'int'
|-ParmVarDecl 0x4df0e80 <col:16, col:20> col:20 used b 'int'
`-CompoundStmt 0x4df10b0 <col:23, line:8:1>
  `-ReturnStmt 0x4df10a0 <line:7:5, col:16>
    `-BinaryOperator 0x4df1080 <col:12, col:16> 'int' '+'
      |-DeclRefExpr 0x4df1010 <col:12> 'int' lvalue ParmVar 0x4df0e00 'a' 'int'
      `-DeclRefExpr 0x4df1030 <col:16> 'int' lvalue ParmVar 0x4df0e80 'b' 'int'

我想為第一種情況編寫一個匹配器,其中 function 的 arguments 之一是可變參數。 AST Matcher Reference ,我發現有一個isVariadic匹配器,盡管正如文檔所說,

Example matches f, but not g or h. The function i will not match, even when
compiled in C mode.
  void f(...);
  void g(int);
  template <typename... Ts> void h(Ts...);
  void i();

有沒有辦法匹配可變參數 function 聲明,並進一步將可變參數聲明綁定到某個節點? 我想做類似functionDecl(has(parmVarDecl(hasType(packExpansionType().bind("parameter_type")))))的事情,但似乎這不可能,因為沒有packExpansionType匹配器。 我在這里錯過了什么嗎?

為了將來參考,我找到了解決方案。 實際上可以在檢查中定義自定義匹配器。

namespace {
    const AstTypeMatcher<PackExpansionType> packExpansionType;
    const internal::VariadicDynCastAllOfMatcher<Stmt, PackExpansionExpr> packExpansionExpr;
}

// You can also use the macros from ASTMatchersMacros.h

...

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM