質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.31%
Raspberry Pi

Raspberry Piは、ラズベリーパイ財団が開発した、名刺サイズのLinuxコンピュータです。 学校で基本的なコンピュータ科学の教育を促進することを意図しています。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

Q&A

解決済

1回答

2755閲覧

pyファイルの再実行(再起動)がしたい

JHG

総合スコア1

Raspberry Pi

Raspberry Piは、ラズベリーパイ財団が開発した、名刺サイズのLinuxコンピュータです。 学校で基本的なコンピュータ科学の教育を促進することを意図しています。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

0グッド

0クリップ

投稿2022/04/18 04:34

pyファイルの再実行を行うため、下記URLのサイトを参考にしました。

リンク内容https://www.delftstack.com/ja/howto/python/python-restart-script/
リンク内容https://terarail.com/questions/33294

その結果、どちらのサイトの方法を試しても、同じく下記のエラーが発生しました。

PermissionError: [Errno 13] 許可がありません

このようなエラーが発生した場合どのように対処すればいいのかを教えて頂きたいです。
また、これ以外にもスクリプトの、ある地点から最初まで戻れるようなコードがあれば教えて頂きたいです。

現在自分は、Raspberry Pi 4 model B 、pythonを使い色々なものを作りたいと考えているところです。初めてまだ1ヶ月のため、無知で申し訳ありません。

わかる方、どなたか教えて頂けると嬉しいです。よろしくお願い致します。

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

y_waiwai

2022/04/18 04:37

再実行とは、なにをどうしたいんでしょうか。 問題が見えません
JHG

2022/04/18 07:22

情報不足で申し訳ありません。 再実行という言い方が正しいのかはわかりませんが、具体的には、そのコードのプログラムが実行されたら、強制的に実行中のスクリプトの一番最初に戻り、最初から実行し直したいというものです。
y_waiwai

2022/04/18 07:35

単にループさせればいいだけでは。
JHG

2022/04/18 07:49

ご意見ありがとうございます。 記載不足だったのですが、mainの中のwhile関数のelse部分から再実行したいと考えており、私の勉強不足なのは明らかなのですが、そこから最初に戻るようなループを組むことができず困っているのが現状です。そこで、そのプログラムを実行するだけで最初から再実行できるようなものはないのかと思い質問させていただきました。
y_waiwai

2022/04/18 08:00

なんか、至極簡単にできることをかえってややこしくしてしまってるだけ、なように思えますが。 そのmainってのを、一つの関数にすればどうでしょう。あとはそれをループで実行させるだけですよ
JHG

2022/04/18 08:50

ご意見ありがとうございます。 そうなんですよね。 多分すごく簡単なことなんですけれども、勉強不足なあまり、自分の知っている知識だけで組むと、本当にうまく動作してくれない状況でして… 仰られた通りやってみたところ、別の問題が発生してしまって… もう少し色々勉強してみる必要がありそうです…
y_waiwai

2022/04/18 09:39

そのコードとエラーメッセージを提示してくれないと具体的なアドバイスはできないわけですが
JHG

2022/04/18 09:56

情けない話ですが、自分自身課題が何かわかってない状態でして、質問を通して課題が見えてきたので、自分自身でもう少ししっかりしたプログラムを組みなおそうと思います。 お時間をとらせてしまい申し訳ありません。 様々なご意見、ありがとうございました。
guest

回答1

0

ベストアンサー

とりあえずPermissionErrorと出た際は、権限周りの問題だと思います。
どのタイミングでエラーが出ているのかは分かりませんが、ファイル実行時であれば、raspberry piにログインしているユーザーにプログラムの実行権限が無かったり、os.execv()実行時にエラーが出ているのであれば多分引数で参照しているプログラムに対する実行権限がないあたりでしょうか。
(os.execv()でエラーが出ているかどうかは、雑な方法ですが、os.execv()の上の行にprint("start")、下の行にprint("end")と入れて、startはコンソールに表示されるが、その後エラーが表示され、endが表示されないかどうかで見分けられると思います。この辺はご経験に任せます)

権限周りは自分が入っているユーザーの情報、実行しているpythonファイルの権限情報(ターミナルでpythonファイルと同じディレクトリに移動し、ls -lで表示されたユーザーと一致しているかどうか。正確にはそのユーザーに対して読み書き実行の権限が付与されているかですが)、os.execv()で指定しているファイルの権限情報(同じく、指定しているファイルと同じディレクトリでls -lをした際の権限情報)が絡んでくると思うので、なかなかこの情報量だとお互い説明は難しいと思います。

あまりいい方法でなく、悪知恵ですが、以下のコマンドを使用すると問答無用で最上位の権限(root権限)を使用してプログラムを実行することができます。
sudo python XXX.py
これに関しては、何も理解しないで実行すると問題が起きかねないので推薦しませんが、とりあえず権限がない(PermissionError)が出たら全権限を持っているユーザーで実行するのは方法としてあります。
(環境によってsudo pythonなんでないって言われるかもしれませんが...)

投稿2022/04/18 05:05

YuuT

総合スコア673

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

JHG

2022/04/18 06:54

コメントありがとうございます。 なるほど、本当に初心者なもので、このエラーに権限が絡んでくることも初めて知りました... とりあえず、教えられたとおりにしてみたところ、startは表示されたものの、endが表示されませんでした... また、環境のせいか sudo python に関してはそんなものないという風なエラーが発生しました。 実は、プログラム作成の締め切りが近く、権限をいじる勉強まで手が出せない状況で... 無知で申し訳ないのですが、現状このほかにスクリプトの、ある地点から最初まで戻れるようなコードというものをなにかご存じでしたら教えて頂きたいです。
YuuT

2022/04/18 08:09

endが表示されないということは、多分os.execv()の部分でしょうね。 とりあえず権限の話は置いておいて raspi使っているとのことですので、(自分も得意ではありませんが)組み込み系のプログラムを作っている感じですかね。 例えば、人感センサーを接続して、センサーの入力をループで受け続け、人が通った時に特定の処理をするとか。 センサーではなく、ボタン入力でもいいですが。 具体的にやりたいこと(何をつなげてどんな信号を受けて信号がどうなったらこういう処理をする)やソースコードを載せてもらえると回答しやすいかもしれません。 (細かいことを言うと特許とかあるかもしれないので、今開発しているのはすごいアイディアでどうしても公開できない!のであれば仕方ないですが...) コメントである通り、あまりプログラムの再起動というものはせず、基本は上手にプログラムを組んでループで回し続ける(入力を待ち続ける)書き方になると思います。
YuuT

2022/04/18 08:24 編集

凄い単純なものだと下の様な感じですかね。 ```Python import time import pigpio GPIO=1 pi = pigpio.pi() pi.set_mode(GPIO, pigpio.INPUT) pi.set_pull_up_down(GPIO,pigpio.PUD_UP) while True:   if pi.read(GPIO) == 1:     print(pi.read(GPIO))     print("検知")   else:     print(pi.read(GPIO))     print("正常")   time.sleep(1) pi.stop(); ``` とりあえずwhileでループを回し続けて、中でif文を使いセンサーの入力情報次第で振り分ける感じです。 これだとelseに行ってもwhileループからは抜けません。 完全予想ですが、time.sleep(1)をwhileループ内に入れ忘れると大変な事(固まる)のでそこだけは注意してもらえればいいと思います。 (やりたいことが違ったらすいません)
JHG

2022/04/18 09:03

沢山のアドバイスありがとうございます! やはりループをうまく使うことが大切なんですね…勉強になります! 今私が作ろうとしているのは、一定の距離内に物体を検知(超音波センサー)したら、それを1枚だけ写真に撮り保存し、lineなどに送るというありきたりなプログラムなのですが、1フレーム単位?でこの動作が繰り返されているので、ループすると膨大な数の写真が送られてくるのが現状でして… if文の条件をセンサーの入力にしてしまうと、上記のようになってしまいとんでもないことになってしまうので、ループ以外の別のところ(写真の保存など)を見直す必要がありそうです。 時間をかけてプログラムを組んで、回答していただいたのに申し訳ありません。
YuuT

2022/04/18 09:21

なるほど 問題点としては物体が一度センサーの範囲に入ったら範囲外に出るまでずっと写真を撮り続けるってことですかね。 アイディアですが、送信フラグを持つ変数を作成し、1度写真を撮って画像を送ったら送信フラグをtrueにする。 送信フラグがtrueの時は、センサーが検知をしても送信は行わず、センサーの範囲外に物体が出た場合に送信フラグをfalseにするという方法がありそうです。 が、複数の物体が時間差でセンサーの範囲内に入ってきた場合、2個目の物体の写真が撮れなさそうですね。 もっとハイレベル(というより他の技術を組み合わせると)物体認識を行える機械学習ライブラリ(YOLOとかが有名)があるので、これと組み合わせて物体にIDを振る機能があれば(ライブラリによってはあったはず)画面に映っている範囲内ではありますが、新しい物体が来ても写真を送信できそうです。 (話が広がりすぎて技術が追い付かないかもしれませんが...) 課題としては、プログラム的な部分(どうやって再起動の関数を使うか)というよりかはロジック的なところ(超音波センサを使用して、写真を撮りたいが、センサの範囲内に物体があると写真を撮り続けてしまう。これの解消アイディア。)を質問として挙げたほうが良いかもしれません。 質問内容からセンサーを使って物体の写真を撮るなんて想像もつかなかったので... 目的ありきのプログラムなので、目的を書いたほうがよい回答がつくと思います。
JHG

2022/04/18 09:52

ご意見ありがとうございます。 そういった方法もあるのですね!本当に自分の勉強不足を実感致しました。 自分自身課題を明確にできていなかったので、この質問を通して課題が明確になり助かりました。 色々とアドバイスを頂いたのに、結果的に趣旨とずれていることになってしまい大変申し訳ないです。 締め切りまでまだ少し時間があるので、今一度自分自身で調べ、プログラムを組みなおすことにしました。 様々なご指摘、アドバイスありがとうございました!
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.31%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問