1 名前:デフォルトの名無しさん mailto:sage [2008/09/21(日) 12:22:12 ] "The duct tape of the Internet" こと、Perlについての質問箱です。 "There's more than one way to do it" ということで、 Perlの奥深さについて皆で語り合い、追求してまいりましょう。 CGIについての質問は板違いです。WEBプログラミング板でどうぞ。 CGIとPerlの区別がつかない人もWEBプログラミング板に行ってください。 ( WEBプログラミング板 pc11.2ch.net/php/ ) CGIの質問は答えが Perlと全然関係ない話に帰着する場合が 多かったりするのでWEBプログラミング板に行って聞いたほうが得ですよ。 このスレでは(CGI以外の)純粋にPerlのみに関係する質問を取り扱っていこうと思います。 スレ違いの質問にはスルーか、速やかな誘導をお願いします。 www.perl.org/get.html ● 2008/09/21 現在の最新版(安定版): 5.10.0 ● 2008/09/21 現在の開発版: 5.9.5 ▼ 前スレ Perlについての質問箱 37箱目 pc11.2ch.net/test/read.cgi/tech/1218449440/ リンク集は>>2-3 Perl 日本語処理の基礎の基礎 >>4 過去スレは>>5-6 あたり
564 名前:デフォルトの名無しさん mailto:sage [2008/11/29(土) 13:46:35 ] Perlプログラミング初心者です。 困っていますので、助けてください。 以下のようなデータを持っています。 ----------------------------------- xおだ 56 80 90 xとよとみ 90 85 45 xとくがわ 90 90 100 ----------------------------------- 1行目は名前のまえにxという印がついている 2行目に各教科の点数(0から100)がスペースで区切られている。 たとえば、左から国語、算数、理科 3行目は殻行 ----------------------------------- このデータから、それぞれの教科の点数による分布表をつくりたいのですが、どのように書いたらいいのか教えてください。 具体的には、 国語の100点は何人で、99点は何人で、、、、0点は何人。 同じように、算数と理科です。 どうぞよろしくお願いします。
565 名前:デフォルトの名無しさん mailto:sage [2008/11/29(土) 14:03:52 ] 「初心者です」って免罪符つけないほうが良いぞ 嫌う奴も居るから
566 名前:デフォルトの名無しさん mailto:sage [2008/11/29(土) 15:22:14 ] >565 この場合は微妙だが、短絡的すぎないかw そりゃ「初心者なので教えてください」は死ねって思うけど、例えば 1ヶ月くらい前にPerlの勉強を始めた初心者です。 Perl/CGIの入門書に載っている、簡単なBBSくらいは作れるようになりました。 とかなら、教える側にしても重要な情報だべ?
567 名前:デフォルトの名無しさん mailto:sage [2008/11/29(土) 15:53:12 ] 「困ってます。助けてください」 も誰にもメリットのない無意味な免罪符。
568 名前:567 mailto:sage [2008/11/29(土) 16:08:50 ] まぁいっか。ただし、記述では書いてやらん。 以下の説明を元に自分で作れないならもう諦めてくれ。 その前に-------- ファイル保存形式は変更可能なら変更したほうが読みやすい。(プログラムがな)。 perlの場合、順番に〜、とか他のプログラムで扱ってるのと同じでもいいけど、 いちいち名前つきデータにしたほうが便利になる。 無意味な空行もなくしていいならなくしたほうがいい。 ---------------- 1:ファイルを開いて変数に移す。 どうゆう構造で格納すればいいのかは使う人が考えてくれ。 リファレンスを使うと望みどおりに格納できる。 2:sortを使ってデータを意図したとおりに揃える。 3:出力して終了 ただし、$name{'おだ'}->[0]; みたいな形式で格納してしまった場合に特定の点数の者が何人いるかを調べるとき、 たぶんデータをループにかけて全チェックせねばならない。 そんだけの用途なら、 $marks[0]->[90] = ('name_1', 'name2'); #つまり国語90点の人全員の名前 と格納したほうが良い
569 名前:567 mailto:sage [2008/11/29(土) 16:11:52 ] まちがた。 $marks[0]->[90] = ['name_1', 'name2']; #つまり国語90点の人全員の名前 こうか どうでもいいか
570 名前:デフォルトの名無しさん mailto:sage [2008/11/29(土) 16:21:14 ] gmplayerに配信元を渡す為に、 ブラウザでasxファイルをクリックしたら起動するように関連付けた 以下のようなものを作ってみました。 #!/usr/bin/perl use strict; use warnings; my $mplayer = 'gmplayer'; my @media ; while (<>) { /=\s?\"((?:http|mms):\/\/.*(?:wmv|wsx|wma|asf|mp3|mp4))\"/; push @media, $1 if ($1 ne ''); } @media ? exec $mplayer, pop @media : die "There is no streaming lines in this asx file!\n"; チェックの為にシェルからasxファイルを引数にして起動したところ、 わざとマッチする行が無いasxファイルでチェックした時には Use of uninitialized value in string ne at ./mp_wp line 11, <> line 1. Use of uninitialized value in string ne at ./mp_wp line 11, <> line 2. (以下略) There is no streaming lines in this asx file! という風に警告を表示されてしまいました。 この警告を出さなくするにはどうしたらいいのでしょうか?
571 名前:デフォルトの名無しさん mailto:sage [2008/11/29(土) 16:42:37 ] >>570 use warnings;の一行を取っ払えば解決
572 名前:570 mailto:sage [2008/11/29(土) 16:51:02 ] >>571 いえ、use warningsのままどうにかならないものかと…。
573 名前:デフォルトの名無しさん mailto:sage [2008/11/29(土) 17:02:05 ] <>を使うのをやめる
574 名前:デフォルトの名無しさん mailto:sage [2008/11/29(土) 17:02:50 ] >>570 defined $1
575 名前:デフォルトの名無しさん mailto:sage [2008/11/29(土) 17:03:18 ] パターンマッチしたならその結果を見てやれよw
576 名前:デフォルトの名無しさん mailto:sage [2008/11/29(土) 17:08:33 ] >>570 >Use of uninitialized value in string ne at ./mp_wp line 11, <> line 1. ちゅうのはあれだ、$1 を ne で扱って評価しとるからで、 ($1 ne '') は ($1) じゃいかんのかね。 パターンマッチからして undef 以外の 0 や '0' が来る筈ない場所だしなあ。
577 名前:デフォルトの名無しさん mailto:sage [2008/11/29(土) 18:55:57 ] >>564 勉強中なんで、腕試し。こんなもんかな?(未検証) open (IN, "Seiseki.txt"); while(<IN>){ if (/(\d+) (\d+) (\d+)/) { $Kokugo[$1]++; $Sansuu[$2]++; $Rika[$3]++; } } close(IN); print "点数 国語 算数 理科\r\n"; for(0..100){ printf("%4d %4d %4d %4d\r\n", $_, $Kokugo[$_], $Sansuu[$_], $Rika[$_]); }
578 名前:570 mailto:sage [2008/11/29(土) 19:06:42 ] >>573-576 ご教示ありがとうございます。 色々やり方があるんですね。if文の()内を(defined($1))にしたら警告が消えました。
579 名前:デフォルトの名無しさん mailto:sage [2008/11/29(土) 20:53:53 ] >>564 勉強中の自分も作ってみた。 my @subjects = qw(国語 算数 理科); my %names_of; open my $in, "seiseki.txt" or die "can't open : $!"; while (<$in>) { if ( /^x(.+)/ ) { chomp(my @marks = split / /, <$in>); for (0..$#subjects) { push @{$names_of{$subjects[$_]}{$marks[$_]}}, $1; } } } close $in; for my $subject (@subjects) { print "≪$subject≫\n"; for my $mark ( sort {$a<=>$b} keys %{$names_of{$subject}} ) { printf "%3d : %3d人\n", $mark, scalar @{$names_of{$subject}{$mark}}; } }
580 名前:デフォルトの名無しさん mailto:sage [2008/11/30(日) 00:12:06 ] ここ宿題スレじゃないんだけど
581 名前:デフォルトの名無しさん mailto:sage [2008/11/30(日) 13:03:38 ] 1ファイルの変換なら perl henkan.pl page1.html > mypage1.html じゃなかったら open ( IN , "page1.html" ) or die; open ( OUT , ">mypage1.html" ); while( <IN> ){ s/こぬにちは/こんにちは/; print OUT; } close(OUT); close(IN); で出来るんですけど、フォルダにhtmlファイルが60個もあるので まとめてやりたいのですが、 My_folder---page1.html,page2.html ………page60.html の全部に一括して処理するにはどう書けばよいでしようか
582 名前:デフォルトの名無しさん mailto:sage [2008/11/30(日) 13:07:12 ] for ( @ARGV ){ open IN, $_ ; # 略 close IN ; }
583 名前:デフォルトの名無しさん mailto:sage [2008/11/30(日) 13:12:18 ] for ( @ARGV ){ open IN, $_ ; while( <IN> ){ s/こぬにちは/こんにちは/; print $ } close(IN); こうでしょうか? 済みません 馬鹿なんで 略無しで書いてくれると嬉しいです
584 名前:デフォルトの名無しさん mailto:sage [2008/11/30(日) 13:24:41 ] >>581 system("perl henkan.pl page$_.html > mypage$_.html") for(1..60);
585 名前:582 mailto:sage [2008/11/30(日) 13:28:24 ] 甘えんなよ、自分で考えろよ…。 後、「初心者スレ」てーのが WebProg にあるからそっち逝ってくんね? 「誘導してください」なんて言ったら切れるぞ?
586 名前:デフォルトの名無しさん mailto:sage [2008/11/30(日) 13:32:23 ] henkan.plは変わりないままで コマンドプロンプトのところで henkan.pl page1.html > mypage1.html のかわりに system("perl henkan.pl page$_.html > mypage$_.html") for(1..60); と書いてリターンでしょうか? すみません バカで。
587 名前:デフォルトの名無しさん mailto:sage [2008/11/30(日) 14:26:34 ] わからない七大理由 1. 読まない ・・・説明書などを読まない。読む気などさらさらない。 2. 調べない ・・・過去スレ、ググるなど最低限の内容も自分で調べようとしない。 3. 試さない ・・・めんどくさいなどの理由で実行しない。する気もない。 4. 理解力が足りない ・・・理解力以前の問題で理解しようとしない。 5. 人を利用することしか頭にない ・・・甘え根性でその場を乗り切ろうとする。 6.感謝しない・・・教えてもらって当たり前。事がすんだらさようなら。 7.逆切れする・・・自分の思うようにならないと逆切れする。
588 名前:デフォルトの名無しさん mailto:sage [2008/11/30(日) 14:45:12 ] >>586 henkan60.plとかの名前で上の1行を保存 perl henkan60,pl で、実行。 試してないんで、うまくいかなくてもかんべんな。
589 名前:デフォルトの名無しさん [2008/11/30(日) 14:57:09 ] 過去ログにもうあったらごめんなさい。 HTTP::Requestで画像ファイル(gif)を取得して、サーバに保存したいのですが、 $response->content()をそのまま保存しても画像になりません。 コード my $req = new HTTP::Request("GET",$url); local $response = $ua->request($req); print "Content-type: text/html\n\n"; print $response->code(); print $response->message(); print $response->content(); open OUT,">> ./maptest.gif"; print OUT $response->content(); close OUT; 環境はwindowsXP perl v5.10.0 Apache2.2です 誘導でもかまいませんので、ヒントをください。
590 名前:588 mailto:sage [2008/11/30(日) 15:02:02 ] ひとつにまとめるななら、 for(1..60){ my $n = $_; open ( IN , "page$n.html" ) or die; open ( OUT , ">mypage$n.html" ); while( <IN> ){ s/こぬにちは/こんにちは/; print OUT; } close(OUT); close(IN); }
591 名前:デフォルトの名無しさん mailto:sage [2008/11/30(日) 15:10:35 ] >>589 Windows なら binmode OUT; で成功するかも
592 名前:デフォルトの名無しさん [2008/11/30(日) 15:13:33 ] 591さん 早速の回答ありがとうございました。 書き込みの部分を open OUT,"> ./maptest.gif"; binmode OUT,":raw"; print OUT $response->content(); close OUT; として、教えていただいた、binmode を付けることで解決しました。 ありがとうございました。
593 名前:581 mailto:sage [2008/11/30(日) 16:10:29 ] 本当に助かりました。ありがとうです!
594 名前:デフォルトの名無しさん mailto:sage [2008/12/02(火) 18:40:44 ] my $q = new CGI; と my $q = CGI->new(); ではどっちがカッコイイ書き方なんでしょうか?
595 名前:デフォルトの名無しさん mailto:sage [2008/12/02(火) 21:12:20 ] new CGI は後方互換な「間接オブジェクト記法」 間接オブジェクト記法にはトラップがあるのが明記されてる が故に CGI->new() の方が良いとされる。 が、現実では頻繁にコンストラクタを呼ぶ時にだけ 間接オブジェクト記法は使われている。 つーことで、new の時はどっちでもいいじゃね?method 呼ぶ時に 間接オブジェクト記法したら「変態さんがいる!」って言われるかも しれんけどさ。
596 名前:594 mailto:sage [2008/12/02(火) 21:18:55 ] >>595 なんと!ありがとうございます。 Perlのオブジェクト関係はもっとキチンと勉強せねば…。
597 名前:デフォルトの名無しさん mailto:sage [2008/12/02(火) 21:20:58 ] 感嘆詞のニュアンスが微妙な気がしなくもないこともなくはないんだが。
598 名前:デフォルトの名無しさん mailto:sage [2008/12/02(火) 21:34:11 ] 変態さんにびっくりしたのでは
599 名前:デフォルトの名無しさん mailto:sage [2008/12/02(火) 22:21:54 ] { package Foo ; sub new { bless {}, shift } sub get { "hoge\n" } } print Foo->new->get ; # 直接ならあっさり # 間接が一個でも混ると #print get new Foo ; # ダメ #print get { new Foo } ; # ダメ print STDOUT get { new Foo } ; print STDOUT get { Foo->new } ; print do{ new Foo }->get ;
600 名前:デフォルトの名無しさん mailto:sage [2008/12/02(火) 22:24:05 ] 確かにこれならMな変態さんと呼ばれても仕方ないな
601 名前:デフォルトの名無しさん mailto:sage [2008/12/02(火) 23:34:03 ] なんと!スープです
602 名前:デフォルトの名無しさん mailto:sage [2008/12/03(水) 07:46:58 ] >>595 「後方互換」てーのは語弊がある書き方だな、、と自己レス perlobj の "Indirect Object Syntax" の項に説明がある。
603 名前:デフォルトの名無しさん mailto:sage [2008/12/03(水) 12:49:12 ] 関数呼び出しの時に & つけたりつけなかったり なんなんですか?
604 名前:デフォルトの名無しさん mailto:sage [2008/12/03(水) 13:26:44 ] >>603 www.kt.rim.or.jp/~kbk/perl-5.8/perlfaq7.html#what_s_the_difference_between_calling_a_function_as__foo_and_foo__ perldoc.jp/docs/perl/5.10.0/perlsub.pod
605 名前:デフォルトの名無しさん mailto:sage [2008/12/03(水) 13:54:41 ] >>604 ありがとうございました。 よくわかりませんでしたが・・・。付けるに超したことはないのかな。
606 名前:デフォルトの名無しさん mailto:sage [2008/12/03(水) 15:36:25 ] >>605 組込み関数を全て覚えてて関数名ダブらない自信があるんなら付けてなくてもいいけど、 それまでは付けた方が良いってリャマの人が言ってた! アンパーサンドなしじゃ関数名がダブったら組込み関数の方を呼びに行っちゃうからね。
607 名前:デフォルトの名無しさん mailto:sage [2008/12/03(水) 17:05:47 ] PBPでは付けるなって言ってるな。 (サブルーチンのリファレンスが欲しい時以外)
608 名前:デフォルトの名無しさん mailto:sage [2008/12/03(水) 17:33:41 ] CPANあたりみても"&"つけてない方が圧倒的に多いし、使えるからといって 組み込み関数とだぶった名前つけたら読みにくくなるだけじゃないか。 あと、サブルーチン呼び出しの&の有無は完全に等価ではなくて、プロトタイプ まわりや引数を省略したときの振る舞いなんかが違うので注意な。 sub f(\@) { my($x) = @_; print join(",", @$x), "\n"; } @array = (1, 2, 3); f(@array); # 1,2,3 &f(@array); # 空文字列 sub g { my(@x) = @_; print join(",", @x), "\n"; } sub g1 {g;} sub g2 {&g;} g1(1,2,3); # 空文字列 g2(1,2,3); # 1,2,3
609 名前:デフォルトの名無しさん mailto:sage [2008/12/03(水) 17:43:06 ] いや普通は付けないが Perl初心者は慣れるまでは付けるようにしておけ、 という事だよリャマ本
610 名前:デフォルトの名無しさん mailto:sage [2008/12/03(水) 18:52:12 ] バッドノウハウ論議って楽しいよな
611 名前:デフォルトの名無しさん mailto:sage [2008/12/03(水) 21:10:02 ] 初心者っぽく見えるから俺はつけない
612 名前:デフォルトの名無しさん mailto:sage [2008/12/03(水) 22:10:49 ] シンタックスハイライトのついたエディタ使えば組み込みとダブるなんて 意識して書かない限りやらないだろ・・・
613 名前:デフォルトの名無しさん [2008/12/04(木) 12:16:49 ] >>608 > sub f(\@) { > my($x) = @_; > print join(",", @$x), "\n"; > } > > @array = (1, 2, 3); > &f(@array); # 空文字列 この結果、ひどいな。。。 いや、昔の perl だと普通か。。。
614 名前:デフォルトの名無しさん mailto:sage [2008/12/04(木) 12:40:56 ] >>613 プロトタイプ指定は「組込関数のように振る舞える」のが肝なので、 わざわざ & を付けて区別するのは何を意図してるの?って感じだ。 ヘンな言葉遣いをすればヘンに解釈されるってだけじゃん。
615 名前:デフォルトの名無しさん mailto:sage [2008/12/04(木) 14:10:34 ] >>614 初心者が 「慣れないうちは&をつけとこっと」 って思って勉強が進む。そのうち関数プロトタイプのことを知り、試す。 「あれ?」 っていうストーリー。
616 名前:デフォルトの名無しさん mailto:sage [2008/12/04(木) 16:17:28 ] &も()も必ず付ける。それが俺のジャスティス。
617 名前:デフォルトの名無しさん mailto:sage [2008/12/04(木) 16:19:21 ] 必ずつける人はPythonにでも行った方が幸せになれる
618 名前:デフォルトの名無しさん [2008/12/04(木) 17:02:44 ] ppm install DBD-mysql するとないって言われるんだが・・俺だけ?? 情報求むm(_ _)m
619 名前:デフォルトの名無しさん mailto:sage [2008/12/04(木) 18:12:16 ] ――なにが幸せかわからないのです。本当にどんな辛いことでもそれが正しい道を 進む中での出来事なら、峠の上り下りもみんな本当の幸いに近づく一歩ずつですから。
620 名前:デフォルトの名無しさん mailto:sage [2008/12/04(木) 18:33:06 ] >>618 「DBD-mysql PPM リポジトリ」でググッて好きなページを参照して。
621 名前:デフォルトの名無しさん mailto:sage [2008/12/04(木) 21:58:48 ] 1から99までに含まれる奇数を出力するプログラムを書いてみたんですけど これ以上短くすることは可能ですか? print$_%2?"$_ ":()for 1..99
622 名前:デフォルトの名無しさん mailto:sage [2008/12/04(木) 22:08:38 ] $_%2&& print for 1..99
623 名前:デフォルトの名無しさん mailto:sage [2008/12/04(木) 22:22:24 ] print $_*2+1,' 'for 0..49
624 名前:621 [2008/12/04(木) 22:46:56 ] >>622 即レスありがとうございます なるほど!! でもそれだと半角スペースがないですよね? できれば半角スペースは入れたかったんですけど… >>623 ありがとうございます 普通に足していく方法ですか 確かに短くなりますねw うまく説明できないんですけど演算を上手くつかって短くしたいんですよね 説明不足ですみませんでした
625 名前:デフォルトの名無しさん mailto:sage [2008/12/04(木) 23:03:57 ] print$_%2?$_:' 'for 1..99
626 名前:デフォルトの名無しさん [2008/12/04(木) 23:59:40 ] >>620 ありがとうございますm(_ _)m
627 名前:621 mailto:sage [2008/12/05(金) 00:59:21 ] >>625 ありがとうございます 偽の場合の式をうまく使ってますね 何か書かないといけないから空のリストを置いてたんですけど これだと無駄がない感じになりますね
628 名前:デフォルトの名無しさん mailto:sage [2008/12/05(金) 02:11:14 ] $,=" ";print 1..99
629 名前:デフォルトの名無しさん mailto:sage [2008/12/05(金) 02:14:04 ] 痛たたた……
630 名前:デフォルトの名無しさん mailto:sage [2008/12/05(金) 02:16:48 ] あ、奇数か。スマソ $,=" ";print grep{$_&1}0..99 短くないな…