- 締切済み
perlのプログラムでエラーが出ます。
普段PHPerなんですがbatchの関係でperlを使用しなければならなくなり書いていたんですが、 下記のソースコードの中でINSERT INTOの部分でエラーが発生してしまいます。 最初selectしている部分はcreate tableで作っているテーブル構成と同じです。 それからサイト名に関するレコード部分は*で隠しています。 よろしくお願いいたします。 #!/usr/bin/perl use DBI; # データソース $d = 'DBI:mysql:a_anime'; # ユーザ名 $u = '************'; # パスワード $p = '************'; # データベースへ接続 $dbh = DBI->connect($d, $u, $p); $sth = $dbh->prepare("select * from tweet where tweetid BETWEEN '1' AND '21562745' limit 5"); $sth->execute; while( @row = $sth->fetchrow_array ){ $priduct_id = @row['3']; $user_url = @row['6']; $sth2 = $dbh->prepare("show tables from a_anime like 'tweet_@row['3']'"); $sth2->execute; @row2 = $sth2->rows; $sth2->finish; if (@row2 != 1){ $sth22 = $dbh->prepare("CREATE TABLE `tweet_@row['3']` ( `id` int(255) NOT NULL auto_increment, `userid` int(25) DEFAULT NULL, `text` text NOT NULL, `product_id` int(255) NOT NULL, `product_name` varchar(30) NOT NULL, `date` varchar(20) NOT NULL, `user_url` varchar(160) NOT NULL, `username` varchar(100) NOT NULL, `flag` int(1) NOT NULL DEFAULT '1', `rev_point` int(1) NOT NULL DEFAULT '1', `t_tweetid` bigint(255) DEFAULT NULL, `rev_id` int(10) DEFAULT NULL, `rev_flag` int(1) NOT NULL DEFAULT '0', `*****_flag` int(1) DEFAULT NULL, `res_info` int(100) DEFAULT NULL, `fav_info` int(255) DEFAULT NULL, `user_img` varchar(200) DEFAULT NULL, PRIMARY KEY (`id`), KEY `index3` (`flag`), KEY `user url` (`user_url`), KEY `t_tweetid` (`t_tweetid`), KEY `index4` (`flag`,`rev_point`,`product_id`), KEY `index5` (`flag`,`product_id`), KEY `index6` (`userid`,`flag`), KEY `index7` (`username`,`flag`), FULLTEXT KEY `index2` (`text`) ) ENGINE=MyISAM DEFAULT CHARSET=utf8"); $sth22->execute; $sth22->finish; } $sth3 = $dbh->prepare("select user_url from tweet_@row['3']"); $sth3->execute; print "@row['3']\n"; print "@row['6']\n"; @row3 = $sth3->fetchrow_array; $sth3->finish; #if ($user_url != $row3){ print @row['2'] ; print "\n"; $sth4 = $dbh->prepare("INSERT INTO tweet_@row['3'] VALUES (@row['1'],@row['2'],@row['3'],@row['4'],@row['5'],@row['6'],@row['7'],@row['8'],@row['9'],@row['10'],@row['11'],@row['12'],@row['13'],@row['14'],@row['15'],@row['16'])"); print $sth4; print "\n"; $sth4->execute; $sth4->finish; } } $sth->finish; $dbh->disconnect;
- みんなの回答 (1)
- 専門家の回答
みんなの回答
- kmee
- ベストアンサー率55% (1857/3366)
@row['1'] みたいな表記がたくさんありますが、Perlでは @row : 配列 row 全体のリスト @row['1'] : 配列rowの一部を抜き出したリスト (スライス) $row['1'] : 配列の添字'1'の要素(スカラー) となります。また'1'とは書きましたが、文字と数値の区別が曖昧なため可能な表記で、普通は、引用符無しに $row[1] 等と書きます。 Perl で気を付ける点として「コンテキスト」というものがあります。 同じ関数やメソッドが、リストのコンテキストとスカラーのコンテキストで違う動作になります。 詳しくは長くなるので、下のURLや「リスト スカラー コンテキスト」で検索したりしてください。 http://perldoc.jp/docs/perl/5.10.0/perldata.pod @row2 = $sth2->rows; これは、$sth2->rows;が返すのは、スカラー値です。 http://perldoc.jp/docs/modules/DBI-1.612/DBI.pod これを @row2 に代入すると、要素数1のリストになります。 if (@row2 != 1){ 上記のように @rowsは常に要素数1のリストです この比較は、スカラーのコンテキストとなるので、 @row2 は 「@row2の要素数」 となります。つまり1です。 ということは、@row2 != 1は$sth2->rowsの結果にかかわらず、常に偽となります。 @row3 = $sth3->fetchrow_array; #if ($user_url != $row3){ Perlでは @row3 : リストrow3 $row3[0] : リストrow3の要素 は関係がありますが、同じプログラム中にある $row3 : スカラー変数row3 はリストrow3とは独立したものになります。 また、PHPで使われているような比較演算子(==,!=,<.>等)は、「両辺を数値と見做して比較する」というものです。 文字列比較には専用の比較演算子( eq,ne,gt等)を使います。 http://perldoc.jp/docs/perl/5.18.1/perlop.pod $sth4 = $dbh->prepare("INSERT INTO tweet_@row['3'] VALUES (@row['1'],@row['2'], Perlの配列の添字は0から始まります。 (変更もできますが、普通はやりません) $row[0]は不要なのでしょうか? また、これらの値に文字列は無いのでしょうか? 文字列を自動でクオートなどはしません。sqlインジェクションの危険もあります。 内容を確認するのなら $sql="INSERT INTO tweet_$row[3] VALUES ($row[1],$row[2],$row[3],$row[4], .. print $sql . "\n" ; などとすればよいでしょう