2016-11-04 17 views
1

sprintfで複数の埋め込み変数を持つSQLクエリを生成しようとしています。R:sprintf混合型変数のリスト

%sというパラメータを持つSQLを別のファイルとして保存し、それをrの中から読み込みます。読みやすさを向上させるため、私はヘルパーを作成しました。

fillSQLQuery <- function(query, params){ 
    #' fill query with params 
    do.call(sprintf, as.list(c(query, params))) 
} 

私のパラメータは、日付、要素、および文字列です。関数に直接渡すと、日付は整数に、私の因子はインデックス(?)に置き換えられます。一方、ベクトル全体をas.characterに変換すると、すべての要素を日付として文字列に処理し、すべての非文字列に対してNAまたは間違った結果を返します。

do.call(sprintf, 
     as.list(c(query,  
     c(as.character(startDateSequence[1]), # POSix DATE 
      as.character(endDateSequence[1]), # POSix DATE  
      lotTypes[1], id_list[1]))))   # string, factor 

私が今までに見つけた解決方法は、手動で日付とタイプを手動で文字に変換することです。しかし、私はそれを行うための任意の「明確な」方法があるかしら、ニシキヘビのように単純で堅牢な何か:

'query {p1}, {p2}'.format(p1=X, p2=Y) 
+0

これは仕事に不可能に近いですあなたの 'params'ベクトルのほんの一例がなくても有効です。最小限の再現可能な例を作成してください。 – Gregor

+1

私は、その関数では、どのように 'params'をベクトルとして渡すのでしょうか? 'as.character'を実行する前に、ベクターはどのように見えるのですか?おそらく、異なる型のオブジェクトに対して' c() 'を使うとすぐにうんざりします。 – Gregor

+0

あなたはどちらにも当てはまります - より明確になるようにベクトルの例を追加しました。 とはい。何らかの理由で、Rのベクトルがリストとして混合データ型をサポートしていると仮定しましたが、そうではありません。単純なリストとベクトルの置き換えの問題を解決: fillSQLQuery(クエリ、リスト(startDateSequence [1]、 endDateSequence [1]、 lotTypes [1]、ID_LIST [1])) –

答えて

2

さて、あなたは再現性の例を提供していないが、あなたの意図が明確であるので、ここですあなたはこの良い例(自己完結型で再現性)にするために提供されている必要がありますコード:

x1 = Sys.Date() # Date 
x2 = Sys.time() # POSIX datetime 
x3 = "hello" # character 
x4 = factor("world", levels = c("world", "something")) # factor 

qry = "Select %s, %s, %s, %s from blah" 

今すぐセットアップが確立されていることを、我々は解決策に取り組むことができます。 list異なるクラスのアイテムを保持するための自然な構造です:

params = list(x1, x2, x3, x4) 

そして、我々はsprintfを使用する前characterに各リスト要素を変換するために、あなたの関数を変更することができます。

fillSQLQuery = function(query, params){ 
    params = lapply(params, as.character) 
    do.call(sprintf, c(query, params)) 
} 

fillSQLQuery(qry, params) 
# [1] "Select 2016-11-05, 2016-11-05 17:19:29, hello, world from blah" 
関連する問題