プロが教える店舗&オフィスのセキュリティ対策術

assoc関数と同じ動作をする関数(ただし、文字列も扱えるようにする)を作成したいと考えています
具体的には、
(setq S '(("1" "a")("2" "b")))
とあったときに、自作した関数(assoc_mojiとします)
(assoc_moji "1" S)
と実行したら
("1" "a")
となるような関数です
また、無い場合はnilを返します

条件分岐で関数を組み込み、成功した場合は結果を返し
そのほかの場合はnilを返すというところまではわかりますが、
その条件分岐で定義する式が全くわかりません。
memberや、equalを使って、リストに含まれていれば、または指定した文字列が一緒ならば、返すなどしましたがまったくうまくいきませんでした。
どなたか、こういう関数を使ってこういう処理をさせればよいという風なヒントだけでもいいので、ご教授お願いします

A 回答 (4件)

多分、再帰の考え方を使って作って欲しいんじゃないかと思います。


試してみたところ、cond, null, car, cdr, equal, assoc_moji でできますね。

基本的な再帰の考え方は、「リストを下って見ていく」というものです。
(assoc_moji key lst)の形で使用するとして、

まずは、lstの先頭要素(上の例で言うところの("1" "a")の部分;car部)が条件に当てはまるかどうかを見ます。当てはまればその要素を返せばよい。
当てはまらなかった場合は、lstの先頭以外の部分(上の例で言うところの(("2" "b"))の部分;cdr部)に対して同じ捜索をかけて、その結果として返ってくるものを返せば良い。
という考え方です。

実際のプログラムとしては、
・lst が空なら nil を返す
・lst のひとつ目の要素を見て、それが条件に当てはまるなら、その要素を返す
・上記以外の場合は、lstのcdr部に関して再帰

色々省略しましたが、再帰の考え方が伝わりましたら幸いです。
    • good
    • 0
この回答へのお礼

丁寧な説明ありがとうございます。
おかげさまで理解し、解けることができました!

質問に答えてくれた方、本当にありがとうございました!

お礼日時:2008/10/03 16:16

まあ, なんかの課題なんじゃないでしょうか>#2.


いちおう
(defun assoc_moji (&rest x) (apply #'assoc x))
で動くかもしれんけど反則だよなぁ.

この回答への補足

返信ありがとうございます
恥ずかしながら、その通り(課題)です^^;
試行錯誤しましたが、どうしても解けなかったので質問させていただきました。

ちなみに私の書いたソースは以下です
(defun assoc_moji(x d)
(cond
((member x (first d) :test #'equal) (assoc x (first d) :test #'equalp))
(t nil)
)
)
(member)のところを(equal)に置き換えたりしてみましたが、うまくいきませんでした。
また、(member)を外して(assoc)だけにしても見ましたがどれもエラーが出てうまくいきませんでした。

補足日時:2008/10/02 21:46
    • good
    • 0

文字列として等しいかどうかは equal で判定できるはずなので、


>memberや、equalを使って、ストに含まれていれば、または指定した文字列が一緒ならば、返すなどしましたがまったくうまくいきませんでした。

というのなら具体的にどう書いてダメだったかを補足してもらうが早いでしょう。
と、#1のTacosanさんと同じ意見。

(eql "foo" "foo")
nil
(equal "foo" "foo")
t

というかLispがCommon-Lispを指しているのなら、自分で定義するまでもないはずなんだけど。
    • good
    • 0

ぶっちゃけ「引っかかっているところ」がよくわからないので, 現状できているところまで出してもらえないですか?

    • good
    • 0

お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!