• ベストアンサー

サブルーチンを変数を使って呼び出したい。

お世話になります。 Perlでサブルーチンを呼び出す場合、 &hogehoge; としますが、 このhogehogeの部分に変数を持っていきたいのですが、 やり方が分からず困っております。 試しに &{$hensu}; とやってみましたが、動きませんでした。 何かやり方はありますでしょうか。 解決策をご存じの方、ご教授よろしくお願いいたします。

  • 2NN
  • お礼率50% (5/10)
  • Perl
  • 回答数5
  • ありがとう数2

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

  • ベストアンサー
  • osamuy
  • ベストアンサー率42% (1231/2878)
回答No.3

サブルーチンへのリファレンスをハッシュに設定して、それをコールするのが素直と思われます。こんな感じ: use strict; sub hogehoge( $ ){ print 'msg: ', $_[0], "\n"; } my %Proc = ( 'hoge' => \&hogehoge ); my $call = 'hoge'; $Proc{ $call }->( 'test' );

2NN
質問者

お礼

お礼が遅くなり申し訳ありません。 この方法を基にプログラミングできました。 誠に有り難うございました。

その他の回答 (4)

回答No.5

Linux マシンで(bashから)これ試してみたら無事 Hello が出ましたよ。 perl -Mstrict -e 'my $name = "mysub"; my $s = \&{$name}; &$s("Hello"); sub mysub {print "$_[0]\n"}' Perl のバージョンは v5.8.6 です。あと先にも書いた方法ですが、 eval 使ってもできましたよ。 perl -Mstrict -e 'my $name = "mysub"; eval qq(&$name("Hello")); sub mysub {print "$_[0]\n"}' これはどちらも strict です。エラーは一切出ません。

2NN
質問者

お礼

遅くなり申し訳ありません。 参考になりました。 ありがとうございます。

  • hara_peko
  • ベストアンサー率28% (11/38)
回答No.4

{ no strict "refs"; #必要な処理 } ・・・と、ブロックで囲んで必要な部分のみ無効にしてしまうとか。

回答No.2

現在 Perl 5.8.6 で試してみましたが、&{$hensu} の方法で呼び出せました。&{$hensu}() も同じです。 これがだめなら eval を使えばいいと思います。 例) $hensu = 'hogehoge'; eval "&$hensu;";

2NN
質問者

補足

ご回答ありがとうございます。 #1さんの補足に書きましたが、strictモードでの状況下でした。 失礼いたしました。

  • galluda
  • ベストアンサー率35% (440/1242)
回答No.1

がると申します。 Perlの5.6系ですと、 #!/usr/bin/perl -w sub foo { print "aaa \n"; } my $a = "foo"; &{$a}(); というプログラムでちゃんと起動するのですが。 このプログラムを実行されるとどんな感じになりますでしょう?

2NN
質問者

補足

ご回答ありがとうございます。 失礼いたしました。 strict モードでの状況で動かないようです。 strict なしで動かしてみたところ、動作しました。 strict の場合、 > Can't use string ("hogehoge") as a subroutine ref > while "strict refs" in use at index.cgi line 52. と出てしまい、サブルーチンが実行されません。 perlのバージョンは5.8.5です。 strictで同じようなことを行える方法はありませんでしょうか?

関連するQ&A

  • Perlのmyのサブルーチンの内外での宣言の違い

    Perlでmyを使う場合、サブルーチンの内外での宣言の違いについて知りたいです。 私はよくある変数をそのプログラム内全体で使う時(カウントするだけの$iみたいなものや、DBのクエリなど)は、同じ変数名をサブルーチン内で毎回宣言するのが嫌(個人的に同じことを重複するプログラムが好きではないという主義)なので、サブルーチンの外でmyを宣言するのですが、myとかはサブルーチン外で宣言するとどんな問題が生じる可能性があるのでしょうか? また毎回サブルーチン内で宣言するのと外部で宣言するのではどういった時に問題になるのでしょうか?もちろんサブルーチンの外でmy宣言した場合はサブルーチンにその変数が引き継がれることは知っています。 リファレンス部分で変わるような記述を見たことはあります。 さしあたって問題を感じでいないのです、ふと疑問に思ったのですが、どうもそれに書かれたソースが少ないので御存知の方がいればぜひ御教授願いたいです。 <例> my $hoge; sub hoge1 { $hoge = 1; } sub hoge2 { $hoge = 5; } と sub hoge1 { my $hoge = 1; } sub hoge2 { my $hoge = 5; }

    • ベストアンサー
    • Perl
  • サブルーチンについて

    下記のようなソースコードを書いたところエラーが出てしまいました。 $sum = $sample2($a); の箇所でエラーが起こっているようなのですが、解決の仕方が分かりません。 &sample1(5,'&sample2'); sub sample1 { ($a,$sample2) = @_; $sum = $sample2($a); print $sum; } sub sample2 { ($a) = @_; $b = 10; $sum = $a + $b; return $sum; } このように、サブルーチンの中に更にサブルーチンを書いて、なおかつそのサブルーチン名を一旦変数に格納して使用する場合はどのようにプログラムを書けば良いのでしょうか?? ""で囲ったりといろいろとしてもダメでした。 もちろん、$sum = $sample2($a); ではなく $sum = sample2($a); のように書けば良いとは思うのですが、一度サブルーチン名を変数に入れてから使用する場合はどのようにすれば良いのでしょうか?? ご回答の程よろしくお願い致します。

    • ベストアンサー
    • CGI
  • 変数名の動的な付け方?

    久しぶりにPerl/CGIを使って 今、少し変わったプログラムをPerl/CGIで作成しています。 そこで、悩みの種がでてきたのでご相談させていただきます。 例 log.cgi ------------------------------------ id<>hogehoge<> pass<>hogehoge<> time<>09/01/01<> ipad<>127.0.0.1<> ... というログファイルがあるとします。 何行あるかは状況によって変わりますので指定できません。 ただ、それはforeach等で対応できるかな?と思いました。 ここで私のやりたいことなんですが。 test.cgiというメインプログラムで上記ログを開いてから 前の項「id<>hogehoge<>」で言う「id」の部分をそのまま変数名にしてやりたいのです。 ログファイルを読み込む → 一行目を読み込み $id = "hogehoge"; とする → 二行目を読み込み $pass = "hogehoge"; とする ... foreachで対応できるかなーと山勘を探って見たのですが 動的に変数を定義するようなことってできるのでしょうか? お答え頂ければ幸いです。

    • ベストアンサー
    • CGI
  • リファレンスをサブルーチンの戻り値にしてもOKですか?

    ■ サブルーチン内部で処理した結果を格納した、配列、ハッシュ、スカラーなどのデータを戻り値として利用する必要があります。その場合、どうするのが標準的なやり方でしょうか? ■ return (配列へのリファレンス, ハッシュへのリファレンス, スカラー); などとやってしまっても問題はないでしょうか? ■ 下のプログラムを試したところ、予想に反しちゃんと 「31415」と表示されました。 #!/usr/bin/perl -w sub subroutine{ my @a = (3, 1, 4, 1, 5); return \@a; } my $b = subroutine{}; print @$b; ■ サブルーチン内部で使用した変数へのリファレンスをサブルーチン 外で使っていいのだろうか? サブルーチンの処理が終了した時点でサブルーチン内部で使用した 変数はメモリーから消去されるのかと思ったものですから。

    • ベストアンサー
    • Perl
  • モジュールに依存するサブルーチンの書き方

    サブルーチンがあるモジュール(例えばLPW)に依存する場合、 「すでにモジュールが読みこまれていれば読みこまず、まだ読みこまれていなければ読みこむ」 というような書き方をしたいのですが、モジュールが読みこまれているか否かを判断するにはどうすればよいでしょうか? また、Cの場合、ライブラリの読みこみは、 フラグを立てて、#ifdef, #ifndef で断するのが定跡だと思うのですが、 Perlの場合はそのような定跡はありますか? もしあればこちらも合わせてご教授いただけるとうれしいです。 宜しくお願いいたします。

    • ベストアンサー
    • Perl
  • Perlのサブルーチンで連想配列(ハッシュ)を渡す

    Perlのサブルーチンで連想配列(ハッシュ)を渡す方法 -------------------------------------- $str=rep::replace(%A,$B,@C); -------------------------------------- sub refidrep ( \%\$\@ ){ my(%A,$B,@C)=(@_); } -------------------------------------- では、上手くいきませんでした。 どのようにしたら、連想配列をサブルーチンに渡せるのでしょうか? 分かる方いらっしゃいましたらご教授ください。

    • ベストアンサー
    • Perl
  • セッション変数の破棄について、いまひとつスッキリしない部分があります。

    セッション変数の破棄について、いまひとつスッキリしない部分があります。どなたか詳しい方是非ご教授お願いいたします。会員サイトからログアウトするときは、$_SESSION=array(),session_destroy(),そしてクッキーの削除で処理をしてきました。特に問題なく動作をしておりますが、もしログアウト でunset($_SESSION[hogehoge])のように変数を破棄した場合、他のuserの$_SESSION[hogehoge]も削除されてしまうのでしょうか?この部分が、ず~っと疑問に残り解決できませんでした。PCが複数 台あれば、実験してたりかめることもできるのですが1台しかないのでそれができません。ネット上で ずいぶん検索して調べましたが、そこら辺のところをスッキリと理解できるように説明されたページも 見当たらないようでした。もしよいWEBがありましたら、そちらのWEBを紹介していただく形でも結構です。よろしくお願いいたします。

    • ベストアンサー
    • PHP
  • mod_perlでグローバル変数的なコーディング

    mod_perlに限ったことではないですが、グローバル変数はあまり使うべきではないとされていますよね。 しかし、スクリプト全体にわたって参照したい「設定値」のようなもの(よくある例としては、スクリプトの冒頭のほうで様々な設定をセットしておくような変数)の場合、いわば環境変数のように、複数のサブルーチンからでも必要時に参照できたほうが便利です。 このような使われ方で、かつ「おやくそく」に従ってグローバル変数を使わずに実現する方法は、ないものでしょうか。 シンボルテーブルを指定して無理やりメインルーチンのレキシカル変数を参照する、なんていう方法も考えてみましたが、どうも「美しくない」し、そもそも名前空間を侵害しているわけで、本末転倒です・・・ 皆さんはどのようにしているのでしょう。 御教授のほどお願いいたします。

    • ベストアンサー
    • Perl
  • require後、関数を実行時にサブルーチンが存在すれば実行させたい

    perlでrequire後、関数を実行時にサブルーチンが存在すれば実行させたいのですが、どうやれば調べられるかご存知でしたらご教授願えませんでしょうか。 foreach(...){ require "$file"; &Print;・・・ここでエラーが出てしまうのを関数が存在する場合だけ実行するようにしたいのです。 } 宜しくお願い致します。

    • ベストアンサー
    • Perl
  • 隔絶されているサブルーチン間の通信の方法

    以下のようなFortranのサブルーチンとモジュールがあります。これを見ると、サブルーチンA,Bはモジュールa,bが別なのでデータ的に隔絶されていることになります。もし、このような場合、サブルーチンA,Bの間で何らかの変数を共有するようなことをしたい場合、どのような方法があるでしょうか。サブルーチンの引数を使うのは混乱の原因になりそうなので、できればmoduleの方で処理できないかと思うのですが。 混乱しそうなところなので、やり方をいろいろ比較して見てみたいと思います。Cではグローバル変数のように全体で共有する変数を用意するのかなと思いますが。 module a end module module b end module subroutine A use a end subroutin B use b end Fortranについてはここでは特設会議室はありませんが、どこかいいところがあるでしょうか。Cの専門家はいろんなことに通じていると思うのでここにお尋ねしました。よろしくお願いします。

専門家に質問してみよう