1

ルビーの各ループの各行の最後にコンマを挿入しようとしています。最後の行にコンマは必要ありません。array.join(',') 機能については知っていますが、この状況では少し混乱しています。

必要なことを行うための最初の試みをどのようにリファクタリングできますか?

重要な行

@headers.each do |header|
          file.puts "`#{table[:source_database]}`.`#{table[:current_name]}`.`#{header[:current_name]}` AS `#{header[:magi_name]}`#{("," unless @headers.last == header)}" if header[:table_id] == table[:id]
        end

フルクラス

class Table < ActiveRecord::Base        
  has_many :headers

  #--------------------------------------------------------------------------------------------------#

  def self.generate
    @tables = Table.select([:id, :source_database, :current_name, :magi_name])
    @headers = Header.select([:id, :table_id, :current_name, :magi_name])

    File.new("magi_generation.sql", "w")
    @tables.each do |table|
      File.open("magi_generation.sql", "a+") do |file|
        file.puts "#Drops current view #{table[:magi_name]} and then recreates it using updated columns"
        file.puts "DROP VIEW IF EXISTS `#{table[:magi_name]}`;"
        file.puts "CREATE ALGORITHM=UNDEFINED DEFINER=`user`@`127.0.0.1` SQL SECURITY DEFINER VIEW `#{table[:magi_name]}`"
        file.puts "AS select"
        @headers.each do |header|
          file.puts "`#{table[:source_database]}`.`#{table[:current_name]}`.`#{header[:current_name]}` AS `#{header[:magi_name]}`#{("," unless @headers.last == header)}" if header[:table_id] == table[:id]
        end
        file.puts "FROM `#{table[:source_database]}`.`#{table[:current_name]}`;"
        file.puts ""
      end
    end

  end

end
4

2 に答える 2

8

これを使用each_with_indexして、現在の要素とインデックスを取得できます。このようにして、配列のサイズを現在の要素と比較できます。

しかし、私はこのアプローチが好きではありません。あなたの場合、ループ内でレコードをフィルタリングしているため、きれいではありません。レコードをフィルタリングしてから、有効なレコードのみをループします。

file.puts @headers.
    # keep only elements where the condition matches
    select { |header| header[:table_id] == table[:id] }.
    # convert each element into a line
    map { |header| "`#{table[:source_database]}`.`#{table[:current_name]}`.`#{header[:current_name]}` AS `#{header[:magi_name]}`" }.
    # merge everything into a single string
    join(", ")
于 2012-06-29T17:10:04.417 に答える
1

最後にコンマと改行を入れて、必要に応じてすべてを処理し、それを String 変数にスローします。完了chopしたら、文字列の最後の 2 文字を削除して、ファイルに書き込みます。

for_file = ""
@header.each do |header|
   for_file << header + ",\n"
end
for_file.chop.chop # Gets rid of last newline and comma
file.puts for_file

私のループ例には、ループで行っていることの範囲は含まれていませんが、重要なことは、それを文字列に入れてから.chop.chop.

file.puts ...また、すべての改行の代わりに、ヒアドキュメントを検討してください。

file.puts <<EOF
SELECT 'nothing'
FROM dual
UNION
SELECT 'something'
FROM dual;
EOF

これにより、SQL が少し読みやすくなり、文字列補間を引き続き使用できます。

これは、自分のスクリプトで文字列補間を使用して SQL コードを生成する方法です。

于 2012-06-29T17:25:07.417 に答える