• ベストアンサー

perlのpushについてです。

お世話になります。perlのpushについてです。 データファイルを読み@XXに入れます。 実際はもうちょっと複雑なのですが、 foreach $DATA (@XX){$CHECK=''; ($A,$B)=split(/\,/$DATA); # $Bには改行コードを含んでいます。 if ($A==1){$A=2;$CHECK=1;} if ($A==2){$A=3;$CHECK=1;} if ($A==3 and $B==1){$A=1;$B=9;$CHECK=1;} if ($CHECK==1){ push(@N,"$A,$B");}else{ push(@N,"$DATA"9;} } として、@Nをファイルに出力すると1行目を除き、 行の先頭になぜか空白が付いてしまいます。 別のスクリプトで読むときに数字以外は削除というような 文を加えても削除できず、 if ( $A eq '1'){・・・・ としたときにマッチしてくれません。 よって、この最初にファイルに書き出す際に空白が付かないように したいのですが、何故付いてしまうのか?、回避方法は? ご指導頂けたら幸いです。 付いてしまいます。

  • Perl
  • 回答数4
  • ありがとう数1

質問者が選んだベストアンサー

  • ベストアンサー
  • sakusaker7
  • ベストアンサー率62% (800/1280)
回答No.4

補足ありがとうございます。 >print OUT "@N"; この、ダブルクォートでくくっているのが原因です。 "$var" とか、"@N"のように変数をダブルクォートでくくった場合 variable interpolation といって、変数の内容が展開されますが 配列の場合は#3の方の回答にある特殊変数$"の内容が要素の間に挟まるようになっています。 そしてその変数のデフォルト値が空白なので、空白が湧いて出てくるように見えるのです。 回避方法は#3の通り$"に空文字列を設定するか、あるいは ダブルクォートでくくらずに print @N; で良いと思います。 以下ドキュメント(perldoc perlvarで確認できます)から。 $" This is like $, except that it applies to array and slice values interpolated into a double-quoted string (or similar interpreted string). Default is a space. (Mnemonic: obvious, I think.)

その他の回答 (3)

  • moon_piyo
  • ベストアンサー率60% (88/146)
回答No.3

こんにちは $" = ""; をつけたらどうでしょう

  • Tacosan
  • ベストアンサー率23% (3656/15482)
回答No.2

#1 の答えがないと無意味であることは感じつつ念の為確認したいのですが, ・お使いのシステムは何ですか? ・「先頭に付いている空白」の文字コードは分かりますか?

  • sakusaker7
  • ベストアンサー率62% (800/1280)
回答No.1

一つ確認したいことがあります。 @Nの出力はどのように行っていますか? その部分を補足してください。

mobius99
質問者

補足

faileに出力で print OUT "@N"; です。

関連するQ&A

  • pushをすると行ができる

    下のような繰り返し文を作ったのですが、 unshiftのところをpushにするとなぜか 1行空いて保存されます。 unshiftだと大丈夫です。 書き込むときに 行があく理由と行があったら行を取るような 方法があったら教えてください。 改行を取る処理で行は削除されると思ったのですが。 foreach (@txt) { $data = $_; $data =~ s/\r//; $data =~ s/\n//; ($id, $tonum, $c_date, $c_status, $chkbox) = split(/,/, $data); if($tonum eq $mynum) { $html .= "<tr><td>$tonum</td><td>$c_date</td><td>$c_status</td><td>$chkbox</td></tr>"; if ( $rec_id < $id ) { $rec_id = $id; } $rec_id++; } } $newmsg = join(',', ($rec_id, $mynum, $date, $status,0)); unshift (@txt, $newmsg); ちなみに$rec_idは一行ごとに一意(ユニーク) のidをつけようとしているのですが、idのつけ方で 効率的な方法があったらご教授ください。

    • ベストアンサー
    • Perl
  • 要素を削除する最適な方法

    たいへん困っています。Perlでプログラムを作成しており配列要素の削除を行なおうとしています。 例えば下のようなデーターをdata.txtファイルに保存しているとしてください。 1,洋服,婦人服,子供服,男性服, 2,時計, 3,アクセサリ, 上のデーターで1行目にある子供服を削除して 1,洋服,婦人服,男性服, 2,時計, 3,アクセサリ, のようにずらしたいのです。 私がとった方法はデーターをopenで開きforeachで行をまず呼びこみます。 if(!open(DATA,"$data")){&error('ファイル読み取りエラー。'); } else{ @data=<DATA>; close(DATA); } foreach $line (@data){ chomp $line; ($no,@sub)=split(/,/,$line); if($no eq 1){ $i=-1; foreach (@sub){$i++; if($sub[$i] eq '子供服'){next;} else{push @newsub,"$sub[$i]";next; } } push @newline,"$no,@newsub\n";} else{push @newcline,"$line\n";} } これで@newlineを表示すると 1,洋服,婦人服, 男性服, 2,時計, 3,アクセサリ, のように男性の前の部分が半角空白として保存されます。 どうしてなのでしょうか?そもそもこういったやり方が間違っているのか、それとも一部だけまちがっているのかもわかりません。お手数ですがどなたか教えてください。

    • ベストアンサー
    • Perl
  • perlでファイルのデータの一部を削除したい

    久しぶりにPerlを操作してファイルのデータの一部を削除したいのですが、削除出来ずに困っております。 3年以上触っていないため、過去のファイル等々を見ながらやってましたが、結果は出来ずじまいで停滞して困っております。 ご指導いただけないかと思い、書き込みしました。 ファイル名 $tmpfile データ構成  no,名称 1<>フレーム 2<>レンズ 3<>カメラ 4<>ファインダー 5<>めがね 6<>ズーム これで「めがね」を削除したいのです。 データnoで削除したいと思っておりますが、うまく動作しません。 以下ソース open(DB,"$tmpfile") || &error("Open Error : $tmpfile"); flock(DB, 1); @lines = <DB>; @new=(); foreach $line (@lines) { $flag=0; ($no,$meisyo) = split("<>", $line); foreach $x (@DEL) { if ("$x" eq $tmpnum) { $flag=1; last; } } if ($flag == 0) { push(@new,$line); } } open(OUT,">$tmpfile") || &error("Write Error : $tmpfile"); print OUT @new; close(OUT); ここまで 上のソースですと、エラーこそならずに(そうみえているだけかもしれません)終わりますが、データ削除が正しく出来ませんでした。 説明不足があるかもしれませんので、指摘いただけますと幸いです。 よろしくお願いいたします。

    • ベストアンサー
    • Perl
  • データの抽出、配列操作で教えて下さい。

    こんばんは、お世話になります。 配列操作で教えて頂きたく。 次のデータをuser.datとします。 1<>yamada<>99999<> 2<>tanaka<>22222<> 3<>suzuki<>10101<> 4<>yamada<>12345<> 5<>yamada<>55555<> user.datの中からyamadaの行だけ取り出して 3番目の数字データでソート表示したいのですが なかなかうまくいきません。 open(F,"user.dat"); @load_txt = <F>; close(F); foreach $data (@load_txt){ if((split(/<>/,$data)[2]) eq "$usid"){push(@txt_lines,$data);} } @txt_lines = sort{(split(/<>/,$a))[2] <=> (split(/<>/,$b))[2]}@txt_lines; 上記でおかしな所ありましたらご教示頂きたく 宜しくお願いします。

    • ベストアンサー
    • Perl
  • 特定の行を編集したい-perl

    特定の行を編集するプログラムを組んでいます。 どうしても2行だったものが1行になってしまいます。 1111,山田,2007/03/10 2222,田中,2007/04/09 3333,南,2007/06/01 ↓↓編集後 1111,山田,2007/03/10↑2222,田中,2007/04/09 3333,南,2007/06/01 になります。↑矢印が出現し2行だったのが1行になります。 スクリプトは、 &read_txt2; foreach (@txt) { # chomp $_; ($tonum, $name, $login) = split(/,/, $_); if ($tonum eq $mynum) { $login = &get_date_string; # $login .= "\n"; $_ = join(',', ($tonum, $name, $login)); } push(@all_txt, $_); } @txt = @all_txt; &write_txt2; Perl逆引き大全600と同じようなスクリプトなのですが・・・ 気になる点としては$loginが空っぽデータであることです。 関係あるでしょうか? 改行コードについてはchompで削除してみたりしたのですが、 駄目でした。変化なし。 ちなみにログイン時にログインした日時を更新していくスクリプトです。

    • ベストアンサー
    • CGI
  • Perl if 文内にforeachを入れる場合

    if ($pattern eq 'p2') { foreach $key (sort{ ($re_key{$b} <=> $re_key{$a}) || $b cmp $a } keys %re_key) { } else { foreach $key (sort{ ($b <=> $a) || $b cmp $a } keys %re_key) { } $pattern の選択で検索の種類を切り替えたいのですが、上のように指定するとコンパイルエラーになってしまいます。 foreach 文以降の処理は全く一緒なので、foreach 文の行だけ変更したいのですが、どうすれば良いですか?

  • Perlでのforeach文の挙動がわかりません

    Perlに詳しい方教えてください。 WinXP(SP3)+ActivePerl-5.10.0.1004の環境で、重複データのチェックプログラムを 作成していますが、foreach文の挙動がよく分かりませんので教えてください。 ※Perlは独学です。 <入力ファイル> あいうえお あいうえお かきくけこ あいうえお <出力期待値その1> あいうえお,重複しています あいうえお,重複しています かきくけこ あいうえお,重複しています <出力期待値その2> あいうえお,重複しています あいうえお,重複しています かきくけこ あいうえお <プログラムの要約> open(IN,$input_file); # 入力ファイルを読み込み @BASE = <IN>; close(IN); @BASE_2 = @BASE ; # 配列のコピーを作成 $count_1 = '0' ; foreach $data_1 (@BASE) {   $count_1++ ; # 何行目を処理しているかのカウンター   $flag_1 = '0' ; # フラグの初期化   $count_2 = '0' ;   foreach $data_2 (@BASE) { # ←★ここの記述方法の質問です★     $count_2++ ;     if ( $count_1 == $count_2 ) { next; } # 自分自身の行とは比較しない     if ( $data_1 eq $data_2 ) { $flag_1 = '1' ; } # 一致したらフラグを立てる   }      if ( $flag_1 == '0' ) { # フラグが立たなかったらそのまま新しい配列へ追加     push(@kekka,$data_1);   } else { # フラグが立ったらコメントを追加して新しい配列へ     $data_1 =~ s/\n//g;     $data_3 = $data_1 . ",重複しています\n" ;     push(@kekka,$data_3);   } } $kekka_2 = join("",@kekka) ; # 配列のデリミタ対策 open(OUT,"> $output_file"); print OUT "$kekka_2"; close(OUT); exit; <質問> 上記プログラムの★マークの箇所で、 foreach $data_2 (@BASE_2) としますと、<出力期待値その1>が得られます そして、 foreach $data_2 (@BASE) としますと、<出力期待値その2>が得られます プログラムの途中で @BASE_2 = @BASE としていますので、一見しますと 同じ処理をしているように感じるのですけれども、実際には出力結果が異なり ますので、何かが違うのだと思います。 その違いを教えて戴きたいです。 ※投稿確認画面でTABが消えてしまいますのでTABは全角スペースに変更して  おります。  見えづらい場合には申し訳ありません

    • ベストアンサー
    • Perl
  • perlで配列を複数行削除したいのですが

    @UserDataNum=qw(11 13 34) @PDataLinesの中身 1<>タイトル<>2009/02/10<>適当なデータ<>適当なデータ2<> 2<>タイトル2<>2009/03/13<>適当なデータ<>適当なデータ2<> .. 50<>タイトル3<>2009/03/23<>適当なデータ<>適当なデータ2<> $TODAY=今日の時間; foreach(0..$#PDataLines){ my@aaa= split(/<>/,$PDataLines[$_]); my$a2 = $aaa[2];$a2 =~s{/}{}g; #ここの処理で@UserDataNumに入っている数字と一致する$aaa[0]を含む行を除外し、時間が今日以降のものを配列@Arrayに入れたいのです if(($aaa[0] !~ /@UserDataNum/) && ( $TODAY < $a2)){ push(@Array,$PDataLines[$_]); } } print "\@Array=@Array"; if(grep(!/@UserDataNum/, @PDataLines) && ( $TODAY2 < $a2)){ としてみたり試みているのですが、思うように出来ずにいます。 どなた様かご教授願えませんでしょうか 宜しくお願い致します。

    • ベストアンサー
    • Perl
  • perlでの三次元配列の作り方

    perlで三次元配列をテキスト入力から作りたいのですが、例えば二次元配列の場合 foreach $line (@input) push @data, [split /[:]/, $line]; で@dataが二次元配列になるのですが、三次元配列の場合このあとに push @output, \@data; とするとリファレンスが同じであるためループをまわしてもうまく三次元になりませんよね。 解決法はありますでしょうか?

  • 要らない配列を無くしたい。Perl

    要素のない配列を消したいです。 do\n be\n usual\n become\n get\n look\n watch\n このような複数行の文があり"a"が入っている行だけ配列に突っ込みたいと思っています。 自分が試した方法として。 @line = split(/\n/,$content); とりあえず改行で区切り配列にぶち込んでいき。 foreach $line (@line){       unless ($line =~/a/){       $line = undef; } } その次に"a"が入っている以外の配列にundefを入れるようにしていました。 しかしこれだとundefが入っている配列がたくさん出来てしまい納得がいきません。 要素のない配列を消したいです。 どなたかご教授お願いします。

    • ベストアンサー
    • Perl