ゲームなんでも屋&プログラミングなんでも屋

ゲーム情報やプログラミングに関してのブログ

Pythonでウェブスクレイピング(ウェブサイトからの情報抽出) 〜ライブラリ紹介とウェブページのソースコードの見方〜

 今回はクローリングおよびウェブスクレイピングという技を紹介したいと思います。クローリングやスクレイピングというのは簡単にいうとウェブサイトに載っている情報から自分が欲しい情報だけを抜き取ってくるための技術です。例えばウェブサイトに載っている写真だけを抜き出したり、特定の数値だけを抜き出したりといった使い方ができます。

 

・用語説明

①クローリング

 ウェブサイトからHTML情報やそのほかの情報を取得してくる技術のこと

スクレイピング

 取得したHTML情報等から自分の欲しい情報を抜き出す技術のこと

 

スクレイピング・クローリングのためのライブラリ

 今回はPythonスクレイピングをするためのライブラリーを紹介したいと思います。

①requests

 こちらはウェブページを取得するためのライブラリです。

②BeautifulSoup4

 こちらはウェブページからデータを抜き出すためのライブラリです。

 基本的に上にあげた二つを使ってクローリング・スクレイピングをする時には、①のrequestsを使ってウェブページの情報を取得し、BeautifulSoup4を使ってデータを抜き出すという形になります。

③Scrapy

 こちらはクローリング・スクレイピングの総合フレームワークとなっていて、このフレームワーク一つでウェブページの情報を取得し解析し特定情報を抜き出してくることができます。より複雑なクローリング・スクレイピングを実装したい時にはこちらを使うといいかもしれません。

 調べてみたら他にも色々フレームワークはあるらしいのですが、今回は自分が使ったことあるやつのみを紹介させていただきました。

 またそれぞれのライブラリの詳しい使い方は今後別記事として紹介したいと思います。と言ってもそれぞれ調べていただければすでにたくさん記事があるので、僕が書くまでもないかもしれませんが。

 

・ウェブサイトのHTML情報を見る方法

 こちらはウェブサイトを作ったことある人なら、スクレイピング・クローリングを使ったことなくても、知っているかもしれません。

  今回は検索エンジンとしてGoogle Chrome を例に、ページとして当ブログを例に使います。

 まずHTML情報を見たいウェブページで右クリックをします。すると下のようになると思います。

f:id:koro_game_and_programming:20200117095844p:plain

 

 ここで検証というところを押します。すると下のような画面となります。

f:id:koro_game_and_programming:20200117100027p:plain

 

 このようにHTMLの情報を見ることができます。

 これだけでもがんばって目視で確認していけば問題はないですが、ここで今回は3つ便利な使い方を紹介したいと思います。

①ウェブサイト上の文字とHTMLの情報の対応づけを見る方法

 上の二つ目の写真の左中央の赤く囲ってあるところをクリックします。するとウェブサイト上の文字とHTMLの情報の対応づけを見るモードとなりマウスをウェブサイト上の文字のところに合わせると下のようにそれに対応するHTMLが青く強調されます。

f:id:koro_game_and_programming:20200117100920p:plain

 

CSSセレクタ等をコピーする

 コピーしたいHTML情報の上で右クリックをすると下のようになります。

f:id:koro_game_and_programming:20200117102400p:plain

 

 ここでCopyというところにいくと下の写真のようにオプション付きでコピーすることができます。ここでCopy selectorをすればCSSセレクタをCopy JS pathをすればjavascriptのパスをといった具合にコピーできます。

f:id:koro_game_and_programming:20200117102645p:plain

 

③HTML情報の特定の文字を含む部分を見つける

 ます検証画面でcommand+Fを押します(Macの場合)。すると下の写真のように下に文字を検索するところが現れます。ここに文字を打ち込めばその文字と一致する箇所を見つけてくれます。例えばclass名で検索すれば同じクラスで書かれた部分を全て見つけることができます。

f:id:koro_game_and_programming:20200117112048p:plain

 

 最後にHTML情報だけを大画面で見る方法を紹介します。先ほどと同様にウェブページで右クリックをします。すると下のような画面になります。

f:id:koro_game_and_programming:20200117112516p:plain

 

 ここで先ほどは検証を押しましたが、今度はページのソースを表示を押します。すると大画面でHTML情報を見ることができます。

 

・クローリング・スクレイピングの使い所

①定期的に更新されるものの情報を抜き出す(例株価、売上情報等)

 定期的に更新されるものを毎回手動でウェブサイトからコピーしてきて手元に保存するのは大変ですよね。そんな時スクレイピングのコードを書いておけば、そのコードを実行するだけで、情報を抜き取ることができます。ただしウェブサイトの構造(htmlに書かれたタグやclassなどのこと)が変わったらスクレイピングのコードも書き直さないといけません。

 

機械学習などのために大量のデータをネットから拾ってくる(例 google検索の画像検索に載っている画像を上から100個ダウンロードしてくる)

 機械学習などで大量のデータが必要な時にそれを全て手動でダウンロードしてくるのは大変ですよね。そんな時にもスクレイピング・クローリングは役に立ちます。何かしらの規則を作ってウェブページを順番に取得し、それらのページに対して処理をしていけばいいです。例えば上の例ではgoogle検索の画像検索で上位から順番に100個目のサイトまでという規則を作り順番にウェブページを取得し、取得してきたページから画像を抜き出すという処理をすれば良いです。

 

 経営者とかだとスクレイピングした情報から経営戦略を立てたりとかに活用されたりもされているようですが、個人で趣味としてやっていることに使えるのはこの辺りかなと思います。いずれにせよ共通しているのは大量のデータを抜き出すという点です。少数のデータを抜き出す場合にはわざわざプログラムを書くよりも手動で抜き出した方が早いなんて場面も多いでしょう。

 

・注意点

 スクレイピングを使うことで、ネットから情報を抽出してくることができますが、この方法はウェブサイトの運営者が公式にサポートしているものではありません。当然著作権に引っかかるような情報を勝手に自分の利益のために公開したりとかしてはいけません。場合によっては訴訟問題に発展しているものもあるようです。スクレイピングできたからといって、権利等を無視して使えるわけではありません。あくまでデータ取得する手間であって、取得したデータの使い方は普通に手動で情報取得した場合と同じです。

 

 今回はスクレイピングおよびクローリングという技術を紹介させていただきました。面白そうと思った人はぜひ実装してみてください。特に大量のデータをネットから拾ってこないといけない作業をしなければいけない人は覚えておくと便利です。

自作関数シリーズ第2回 sin関数 (C言語、Java、Python、Ruby)

このシリーズは普段ライブラリを利用して求めているような計算を自作するとしたらどのようなコードになるのかを紹介するシリーズです。といってもOpenCVやBeautiful Soupのような大規模なライブラリの関数を自作するわけではありません。大規模なライブラリは眺めてこんな感じ何だなって理解するに留めて、素直に作ってくれた人に感謝して利用しましょう。さて第2回ではsinを求める関数を自作したいと思います。ちなみに普通にsinを求めるには

C言語: include<math.h>をしてからsin関数を使う

Java: Mathクラスのsinメソッドを使う

Python: import mathをしてsin関数を使う 

Ruby: Math.sinを使う

 

自作関数シリーズ第1回(ルートを求める関数)

https://koro-game-programming.hatenablog.com/entry/2019/12/31/205914

 

さて、ます今回sinを求めるにあたって使う数学的な知識から入ります。今回sinを求めるのにはマクローリン展開という方法を使います。

これは下のような式で表される展開です。大学で理系の方なら少なくとも一度は聞いたことあると思います。

f:id:koro_game_and_programming:20200111001746p:plain

そしてf(x) = sin(x)として上の式に代入した結果が下のようになります。

 

f:id:koro_game_and_programming:20200111002301p:plain

この式を元に実際にsinを求めるプログラムを書いてみると下のようになります。ちなみにコンピューターに無限回計算させるわけにもいかないので、今回はxの19乗の項までの近似計算としています(この程度のループでもかなり良い精度となる)。ちなみに今回は変数sumを第n項までの合計を保存するための変数、tを各項を求める変数としています。そしてまずtとsumにxを代入、次にtに

-(x*x)/( (i*2)*(i*2+1) )をかけることで-x^3/3!を求め、それをsumに加えます。さらにこの操作を第10項目まで繰り返しています。

 

C言語

double my_sin(double x){
 double sum = x;
 double t = x;
 int i;
 for(i=1;i<10;i++){
  t *= -(x*x)/( (i*2)*(i*2+1) );
  sum += t;
 }
 return sum;
}

 

Java

public static double my_sin(double x){
 double sum = x;
 double t = x;
 for(int i=1;i<10;i++){
  t *= -(x*x)/( (i*2)*(i*2+1) );
  sum += t;
 }
 return sum;
}

 

Python

def my_sin(x):
 sum = x
 t = x
 for i in range(1,10):
  t *= -(x*x)/( (i*2)*(i*2+1) )
  sum += t
 return sum

 

Ruby

def my_sin(x)
 sum = x
 t = x
 for i in 1..10 do
  t *= -(x*x)/( (i.to_f*2)*(i.to_f*2+1) )
  sum += t
 end
 return sum
end

 

ちなみにマクローリン展開を使うことでcos,tan,log(1-x),exp(x)なども近似的に簡単に求めることができるので気になったら作ってみてください。

環境構築のコツ スムーズに環境構築を行うために

 プログラミングの勉強をしようと思って、本を買ってきて環境構築をしようとしたら、本に書いてある通りにやってるのになんかエラーが出てくる。あるいは、ネットで調べた記事通りに環境構築をしていたら、エラーが出てくる。みなさん今までにこんな経験はありませんか?僕は今までこういったことが何回もありました。そして1年くらい前までなんとなく適当にエラー文をgoogleの検索に打ち込んで上から順番に見ていってエラーがなくなるまで調べ続けるということをしていました。おそらくこの方法でもネットに正しい記事があればいずれは解決すると思います。しかしこれってすごく疲れますよね?初心者は訳もわからないエラーと永遠に戦うことになり、時にはそこで諦めてしまうこともあります。今回は少しでも環境構築をスムーズにするためのコツを初めてプログラミングするような人にもわかりやすく書きたいと思います。

 

・そもそもなぜ環境構築でエラーが出るのか

 本やネットに書いてある通りにやっているのにエラーが出る。これは何も本やネットの記事を書いている人がみんなを困らせようと思って、嘘を書いているわけではありません(もしかしたらそういういじわるな人もいるかも)。じゃあなぜエラーが出るのかというと、多くのソフトウェアやライブラリーは少しずつ改良されているからです。この改良というのが厄介で改良されるのは確かにいいことなのですが、古いバージョンにあったよくない仕様等は消されていってしまうことがよくあるんです。その結果古いバージョンでうまく動いていたものでも、新しいソフトウェアやライブラリーでは動かないということが起きます。

 

・環境構築をスムーズに行うために意識すべきこと

①ソフトウェアやライブラリーのバージョンを意識する

②自分が読んでいる本や記事がいつ書かれたものかを意識する

③すでに自分のパソコン上に作られた環境を意識する

 

 初心者の方々だとそもそも、バージョンがいくつもあることや、バージョンが違うと互換性がないということに気づいていない人が多いかなと思います。僕も独学でやっていたので最初しっかりバージョンというものを意識できておらず、環境構築で戸惑っていました。この二つを意識しておけば闇雲に検索してエラーが出続ける、環境構築の闇にハマることも少なくなると思います。

 

・ケース別の対処法

①そもそも環境構築でエラーを出さないようにする方法

・ネットの記事を読む場合

 この場合、記事が書かれた日付を意識します。そして何かプログラムをパクってくる時はなるべく新しいものからパクってきます。もしくは古いバージョンからパクってくる場合でもしっかり記事にバージョンが書かれているものからパクってくる(ネットの記事って結構適当で動くことを確認した環境をしっかり書いてくれている記事が少ないです)。ちなみにパクってきたプログラムをそのまま使うだけならこれでエラーは出ませんが、多くの人はパクってきたプログラムを自分なりに改良していくと思うので、そういう時エラーが出ないためにも新しめの記事からパクってくる方が、少なくとも初めのうちはおすすめです(自分の環境は新しめのバージョンであることを想定)。

 

・本を買う場合

 本を買う時意識すべきなのは発行年数です。発行年数が新しければ新しいほど、本に書かれた通りやるだけで、うまくいく場合が多いです。初めのうちって本に書いてある結果と自分の結果が少しでも違ったりすると自分のやってることあっているかな?とか不安になるものですし、本と同じ環境でやることは大切だと思います。ただし本の場合、ネットの記事と違ってソフトウェア等のバージョンがしっかり書いてあるので、そのバージョンを指定してやればそんなに困ることはないかもしれません。ただ本も不親切な場合があって、文章ではバージョンを書いてあるのに、コードではバージョンを指定していない(この場合普通は最新バージョンがダウンロードされる)場合があります。ある程度プログラミングをやっている人であれば、自分でバージョン指定しなきゃって意識できますが、初心者の方、ましてや初めてプログラミングする方はそんなこと意識できるはずもありません。そして書かれたコードを打ち込んだら、最新のバージョンがインストールされて、挙動が本と異なることがあります。だから初心者の方でとりあえず本を買うなら新しい本買った方がいいかなと思います。プログラミングは面白いと感じるのに、環境構築でつまらないと感じて諦めてしまったらもったいないです。それに基本的にはバージョンアップは改良なので、どうせなら最新バージョンを学んでおいた方が、本の内容を理解した後自分で何か作る時に、その環境のまま最新のものを動かせて便利だと思います。

 

②環境構築でエラーが出てきたときの対処法

 ①では最新のものを見ることでエラーをそもそも出さないようにするといいという説明をしてきましたが、当然記事や本しかない事やあえて古いバージョンのものを動かしたい場合もあると思います。そこで②ではエラーが出てきた時にエラーを解消していくコツを説明したいと思います。まず一番簡単な方法は詳しい人に聞くということです。しかし多くの人は周りにそのような人がおらず、ネットでエラーについて調べると思います。そこで今回はネットでエラーを検索するときのコツを紹介します。

・まずは自分の動かしたいプログラムに必要なバージョンを意識する。

 これがわかればそのバージョンをインストールするだけで解決するので早いです。

 

・記事の書かれた時期を意識する(使うべきバージョンがわからない場合)

 使うべきバージョンがわからないなんてことは、記事をあげている人が親切であれば、起きることもないですしあって欲しくはないのですが、こういう場合も多々あると思います。こういう時はまず記事が書かれた時期を意識しましょう。まず絶対に言えることは記事を書かれた時期よりも未来のバージョンに対応しているという保証は絶対にない。ここで保証がないといっているのは、バージョンが違っていてももちろんそのまま動くことはあるので、動かないと決まっているわけではないからです。では実装したいプログラム等が書いてある記事が書かれた時期と同じくらいの時期に書かれた記事を読めばいいのかというとそれも違います。なぜならその記事が書かれた時期にはまだそのエラーで困っている人はいないからです。バージョンが切り替わって今まで使えていたものにエラーが出るようになった時期に初めてそのエラーへの対処法が書かれた記事が書かれます。そこでそのエラーが出るようになったバージョンへ切り替わったタイミングを意識して、それを調べていくようにしましょう。

 

・正しい対処法が書かれているにもかかわらずうまくいかない場合

 これが一番厄介な場合です。こんなことはありえるのかということなんですが、残念ながらあり得ます。どういう時に起きるかというと、例えば間違ったバージョンをインストールした後、アンインストールしたつもりでもパス(どのプログラムを参照したらいいかを指定するよなもの)にその情報が残っている場合などです。こうなってくると非常に厄介で、正しい対処法を実行してもうまくいかなくなることがあります。しかも厄介なのは正しいかどうかというのは環境構築している時にはわからないということです。この場合は意識すべきこと③に書いた「すでに自分のパソコン上に作られた環境を意識する」というのを思い出して、一旦落ち着いて自分の環境にインストールされているもの、設定されているパスの中で関係ありそうなものを、整理しましょう(こんなこと言ってますが、おそらく初心者には無理)。まあこの段階はもう環境構築の闇にハマってしまっているので、頑張るしかないですね。この闇に陥らないための一つの方法として仮想環境というものがあります。仮想の環境を作ることで、その仮想の環境外に影響を与えることなく環境構築を行えます。このあたりは話だしたらキリがないので、ネットで「仮装環境」と検索してみてください(気が向いたらいつか記事書くかも)。

 

最後に繰り返しとなりますが大切なことは

①ソフトウェアやライブラリーのバージョンを意識する

②自分が読んでいる本や記事がいつ書かれたものかを意識する

③すでに自分のパソコン上に作られた環境を意識する

です。環境構築を突破して楽しくプログラミングしていきましょう。

プログラミング勉強法(独学で初心者から中級者へ)

自分の経験を元にプログラミングを何もできない人が独学である程度プログラミングができるようになるまでの勉強法を説明していきたいと思います。僕のプログラミング経験としてはウェブアプリ制作、画像処理、音声処理、機械学習、ウェブスクレイピング、簡単なゲーム制作などがあります。3日前にはandroid studioスマホアプリを作ろうと思いandroid studioの勉強を始めました。

ただプログラミング経験は2年ほどですし、プロでもありません。あくまである程度プログラミングができるようになるまでの勉強法と思って読んでください。逆にプログラミング経験がプロのように長くはないので、プログラミング初心者の頃を思い出しやすく書きやすいと思いこのタイミングでこの記事を書くことにしました。ちなみにここでいうプログラミングはHTMLなどのマークアップ言語やLispなどの関数型言語などではなくC言語Pythonのような命令型プログラミング言語で書くプログラミングを想定しています。

 

・プログラミング学習で大切なポイント(初めて学ぶ時)

①あくまで学習するべきなのは形ではなく考え方

 よく知り合いとかでもプログラミングを学んでいてfor文の書き方はみたいなのを暗記するところから学習を始める人がいますが、最初から暗記する必要はありません。というか暗記する必要は基本的にありません。プログラミングにおいて書き方は正直どうでもいいです。for文の使い方さえわかっていれば書き方は調べればわかります。そしてよく使う言語であればそのうち自然に覚えます。逆に滅多に使わない言語で書き方忘れていたら、使う時に調べればいいです。とにかく形では無くこういう時はこういう方法を使うとうまくいくということを学びましょう。

 

②インプットよりもアウトプット多め

 基本が書かれた本の第一章を何周もしたり、ノートに構文をまとめたりしている人もいますが、基本的にこういったことは意味がないです。こんなことをするくらいだったらさっさと本を一周して実践しましょう。ただこれは適当に斜め読みすればいいということではないです。大切なのは読むだけじゃなくて書くことです。全てを理解しなくてもいいのでまずしっかり書いて動きを確かめましょう。ポイントは書き方を覚えるために書くのではなく、動きを理解するために書くということを意識することです。小学生の時にやったような漢字練習帳とは書く目的が違います。そして、ここを変えたらどうなるかな?といった興味を持ちながらコードを少し書き換えたりして動きを確かめるとさらにいいでしょう。こういった勉強をしているうちに、こういうことしたい時にはこの方法を使えばいいといったことがわかるようになります。

 

③プログラミング習得のゴールは調べながら、色々なものを作れるようになること

 ここでいうゴールはあくまである程度プログラミングができるようになるという意味でのゴールです。ただこの段階まで来れば基本的に困ることはないでしょう。多くの人が到達したいレベルであるウェブアプリを作れる人になる、スマホアプリを作れる人になる、サーバー管理をできる人になる、機械学習をとりあえず利用する人になるなどであれば全然困りません。そもそも世の中にプログラミングのための便利な道具(フレームワークや開発環境、ライブラリーなど)は無数に存在していてそれら全部を覚えている人なんていません。必要になった時覚えればいいのです。もちろん世の中にまだ方法がないようなことを生み出したりしたいのであればこの段階では不十分かもですが、その段階まできたらそれはもはや研究レベルの話であって、プログラミング技術の問題ではないことも多いでしょう。とにかくここで大切なのは調べながら実装できればいいということです。

 

④完璧主義をやめること

これはここまで書いた①〜③のポイントのまとめとなるのですが、プログラミングは完璧を求めていたらキリがありません。完璧主義はやめましょう。完璧主義の人はまず形を覚えなければと思い、調べているようではまだまだだとかんじ、頑張ってインプットしてしまいます。大事なところはそこではないので、完璧主義はやめたほうがいいです。

 

・プログラミング学習の手順

①まずはプログラミングの基本を学ぶ

この段階でのポイントは5つあります。

その1 本やProgateなど一定のレベルにまとまった教材を使う

いくら独学とは言え何もわからない段階で、ネットに書かれた記事をつまみながら読んで学ぶのは無謀です。素直に本やProgateなどの教材を使って、基本を学びましょう。(個人的にProgateのプログラム書く部分って答えが決まっていて、少し変えたらどうなるかなとかを確かめられないのが好きではないですが(友達がやっているのを見ていてそう思っただけでやったことはないので間違っているかもしれません))

 

その2 基本とはどのレベルなのか

僕が思う基本というのは、変数に代入した時の挙動や変数の型、if・for・whileなどの基本構文の使い方や使い所、関数やクラスの使い方および使い所などです。大事なのは書き方ではなく使い方や動きを学ぶというところです。

 

その3 一つの言語を学ぶ

何度も言っているように、プログラミング学習で大切なことはプログラミングの形式(例えばif文の書き方や関数の書き方)ではなく、プログラミングで利用できる考え方や構造を学ぶこと(例えばfor文というループ構造がある。関数やクラスを利用することで効率よくプログラミングできるなど)です。しかしいきなり色々な言語に触れてしまうと、それぞれの言語における書き方の違いに混乱してしまい、肝心のプログラミングの考え方を学ぶことができなくなります。それに焦って色々な言語を同時にやらなくても、一つの言語で書けるようになれば、調べながらではありますが他の言語でも同じことを書けるようになります。

 

その4 高度なライブラリーやフレームワークを使わない

これは高度なライブラリーやフレームワークは引数を指定したり、パスを設定したりするだけで様々なことができたりしますが、これだと実際プログラムがどのように動いているのかは何もわからないですし、基本を学ぶには向いていないからです。高度なライブラリー等をいきなり使うことで混乱してしまうこともあるでしょう。まずは実際に役立つようなプログラムを作ることを意識するのではなく、基本を理解することを意識しましょう。

 

その5 インプット:アウトプット = 1:1

最初にアウトプット多目が大切と書きましたが、この段階ではインプットとアウトプットは同じ割合でいいでしょう。基本的に一つのことを学んだら、それを使ったコード(本や教材に書いてあるものでよい)を書くといった感じですね。

 

学ぶ言語はどれがいいのか?

自分のやりたいことに使う言語から学ぶもしくは簡単めな言語(PythonRubyPHPなど)から学ぶのが良いでしょう。

下の記事ではPythonを勧めています。

https://koro-game-programming.hatenablog.com/entry/2019/12/14/182627

 

では次の段階に進みましょう

 

②とりあえず簡単なプログラムを自分で考えながらいくつか作る

この段階でのポイントは3つあります。

その1  今まで習ったことを組み合わせたプログラムを書く

 おそらく段階1ではほとんど一つのことを理解しているだけで作れるプログラムを書いてきたと思います。例えばif文を使うだけ、関数を一つ作るだけなどのプログラムです。第2段階ではそれらを組み合わせてプログラムを書いていきましょう。本や教材がある場合にはその本や教材に載っている問題をやってみるといいでしょう。そのような物が無くて無料で済ませたい場合には下のURLに書かれた問題のうち上10個位をやってみるといいでしょう。ただしこの問題だけだと問題に偏りがあるので不十分かもしれないです。ここで大切なことはやり方が思い浮かべば、あとは書き方を調べながら実装できればいいということです。実際にスラスラコードを書けなくてもこの段階では当たり前です。安心してください。

http://vipprog.net/wiki/exercise.html

 

その2 カンニングオッケー

 例えばこのプログラムこういう関数をif文とwhile文を組み合わせて作ればいいななどということが思い浮かんだら、ネットをカンニングしながら書けばいいです。プログラミングにおいてカンニングは何年経っても大切なことですし、ここでネットから自分に必要な知識を見つけるスキルを身に付けるといいでしょう。何年経ってもカンニングが大切というのは、どんなすごいプログラマーであっても初めて使うライブラリーの関数の引数に何を入れればいいかなどということはわからないからです(もちろんライブラリーにあるような関数も全て1から作っていけば実装可能だとは思いますが、普通そんなことはしません)。つまりどんなプロも初めて何かを作る時にはまずそれを実装するのに使えそうな便利な道具を調べるのです。

 

その3 完全なパクリはやめる

 上でカンニングオッケーと言ったのにパクリはダメとかなんじゃこりゃと思う人もいると思いますが、上でカンニングオッケーと言ったのはあくまで部品のカンニングはオッケーと言うだけで、ただ全てをコピーしてくるのがオッケーと言うことではありません。ただコピーしてきただけでは当然何も学べません。最初はしりとりのプログラムを参考にしながら頭とりのプログラムを書くとか、フィボナッチ数列のプログラムを参考にしながら、自分が考えた漸化式の問題をとくプログラムを書くなどだいたいパクリだけど完全にパクリではないといった問題から初めてもいいでしょう。

 

ここまで来たらだいたいのものは作れるようになります

実際に自分の作りたいものを作ってみましょう

 

③実際に作りたい高度なアプリなどを作る

この段階でのポイントは3つあります。

その1 まずは自分の作りたいものを作るのに役立つライブラリーやフレームワークを書籍やネット等で調べる

 ここで初めてライブラリーやフレームワークを調べます。そしてそのライブラリーやフレームワークで利用できる関数やシステムを学んで実際に使っていきます。この段階まで来たら、便利な道具をどんどん使っていきましょう。この段階でimportなどを使うようになると思うので、同時に自分の書いた別のプログラムもimportできることを学ぶといいでしょう。

 

その2 自分の実装したいものに近いものを見て学ぶ

 おそらく高度なアプリを作る時、自分がイメージしているものと全く同じものを作っている人はいませんが、部分ごとでみると似たものを作っている人はいると思います。そういったものを見て自分の作りたいものにどこが利用できるかを考えることは大切です。ブログやgithubなどを覗いてみましょう。段階2でカンニングしっかりカンニングしていた人はこの作業でそんなにつまずかないでしょう。

 

その3 エラーは出て当たり前

いきなり全てうまくいくことなんて滅多にありません。エラーが出たら直して、例外が出たら直してと言うのを繰り返してプログラムを完成させます。このエラーを直していくと言う作業がプログラミングの肝だと思います。もちろんここでもネットや書籍を参考にしましょう。

 

プログラミングは独学でも学べるのか?

個人的な意見としては独学でもいいと思います。このように思うのはプログラミングにおいて誰もが知っておかなければいけない基本というのはとても少なく、あとは実際に作りたいものに合わせて、それを作るのに必要な知識を習得していけばいいからです。

そもそもおそらくですが、世の中にある全ての言語の全てのライブラリーの全ての関数の使い方を覚えている人なんていません。なぜなら世の中の便利なライブラリーは無数とありますが、それらを全て使うような開発はないからです。そしてライブラリーやフレームワークなどの使い方はネットや書籍で調べればわかります。

実際プログラミングスクールでどのようなことをやられているのかは残念ながらわかりませんが、プログラミングを書くという観点で見たらプログラミングスクールにわざわざいく必要はないかなと思います。詰まった時にやり方を聞けるような知り合いはいたほうがいいかもしれませんが。僕もプログラミングスクールには通っていませんが、ある程度実力がついてからはプログラミングをするインターンやプログラミングを利用する団体などに入って実際に使えるプログラミングを学びました。

逆にすぐ特定の仕事に直結する知識だけを学びたいという方や案件をすぐに勝ち取りたいという方はプログラミングスクールを利用されるのがいいかもしれません。プログラミングスクールが仕事に結びつくまで面倒を見てくれる場合も多いようです。

 

以上長々と書いてきましたが、プログラミングは継続さえすれば、少なくとも世の中にすでにある技術を利用してプログラムを書くというレベルには誰でもなれると思います。だってプログラミングって英語に比べて文法は簡単、わからなかったらカンニングすればいい、リスニングもスピーキングもない。こう聞くと誰でもできそうですよね。プログラミングを習い始めたばかりの人、これから習おうという人、頑張ってください!

自作関数シリーズ第1回 ルート関数 (C言語、Java、Python、Ruby)

このシリーズは普段ライブラリを利用して求めているような計算を自作するとしたらどのようなコードになるのかを紹介するシリーズです。といってもOpenCVやBeautiful Soupのような大規模なライブラリの関数を自作するわけではありません。大規模なライブラリは眺めてこんな感じ何だなって理解するに留めて、素直に作ってくれた人に感謝して利用しましょう。さて記念すべき第1回はルートを求める関数を自作したいと思います。ちなみに普通にルートを求めるには

C言語: include<math.h>をしてからsqrt関数を使う

Java: Mathクラスのsqrtメソッドを使う

Python: import mathをしてsqrt関数を使う

Ruby: Math.sqrtを使う

 

今回ルートを求めるのに使う方法はニュートン法です。

ニュートン法は「f(x) = 0になるような値Xを探す時、ある値Xnにおける接線の切片Xn+1は、元の値Xnより真の値Xに近くなる。」という考え方に基づいています。

この考え方を数式に直すとXn+1とXnの漸化式は

Xn+1 = Xn - f(Xn)/f'(Xn)

となります。

下の図を例に見てみると確かにXn+1はXnよりも真の値Xに近いことがわかります。

ニュートン法の数学的な説明をもっと詳しく知りたい人は

wikipediaなどを参考に読んでみてください。

https://ja.wikipedia.org/wiki/%E3%83%8B%E3%83%A5%E3%83%BC%E3%83%88%E3%83%B3%E6%B3%95

 

f:id:koro_game_and_programming:20191231182645p:plain

 

さて今回の本題ルートを上で紹介したニュートン法で求めていきましょう。

x = √a

と置き式変形すると

x^2 - a = 0

ここで左辺をf(x)と置くと

f(x) = x^2 - a

f'(x) = 2x

これを上の

Xn+1 = Xn - f(Xn)/f'(Xn)

に代入すると

Xn+1 = Xn - (Xn~2 - a)/2Xn

         = Xn/2 + a/2Xn

これを繰り返していくと近似的にルートを求めることができます。

最後に実際にこの漸化式を10回繰り返し近似的にルートを求めるプログラムを紹介したいと思います。今回は10回漸化式を繰り返す方法をとりましたが、自分で近似の精度を決めたい場合はwhile(True)で回し続けて精度がよくなったらbreakで抜けるという方法を取れば良いでしょう。

 

C言語

double my_sqrt(double x){
 int i;
 double y,z;
 if(x==0){
  return 0;
 }
 else{
  y = 1;
  for(i=0;i<10;i++){
   z = x/y;
   y = (y+z)/2;
  }
  return y;
 }
}

 

Java

public static double my_sqrt(double x){
 if(x==0){
  return 0;
 }
 else{
  double y = 1;
  for(int i=0;i<10;i++){
   double z = x/y;
   y = (y+z)/2;
  }
 return y;
 }
}

 

Python

def my_sqrt(x):
 if x == 0:
  return 0
 else:
  y = 1
  for i in range(10):
   z = x/y
   y = (y + z)/2
  return y

 

Ruby

def my_sqrt(x)
 if x == 0
  return 0
 else
  y = 1.0
  for i in 0..9 do
   z = x/y
   y = (y+z)/2
  end
 return y
 end
end

絶対に覚えておいた方がいいターミナル(端末)のコマンドおよび使い方〜その3〜

その3ということで今回は覚えておいたほうが良いが覚えていなくてもそこまで不便ではないコマンドを紹介したいと思います。

 

・mkdirコマンド

これはmake directory の略で空のディレクトリーを作るコマンドです。Finderで右クリックすることでもディレクトリーを作れるので、使い分けると良いでしょう。

 

・rmコマンド

これはremoveの略ファイルを削除するコマンドです。Finder からゴミ箱に入れるのと違う点は、ゴミ箱に入れるの場合間違って入れてしまっても復元することができるが、このコマンドで削除すると完全にパソコンからファイルが消えます。よくわからないうちに大切なファイルを消してしまったりする恐れがあるので、確実にいらないとわかっているもの以外には慣れてないうちは使わないほうがいいでしょう。

 

・mvコマンド

これはmoveの略でファイルを移動したりファイル名を変更したりするコマンドです。

mv test.txt test/

とすればtest.txtがtestフォルダに移動します。

またmv test.txt test2.txt

とすればファイル名がtest.txtからtest2.txtに変わります。

ただfinderから操作したほうが直感的で楽にできると思います。

 

・cpコマンド

これはcopyの略でファイルをコピーします。

cp test.txt test/

test.txtの内容をtextフォルダ内にコピーします。

cp test.txt test2.txt

とすればtext.txtの内容をtest2.txtにコピーします。

こちらもとりあえずはfinderからやっても問題ないでしょう。

 

3回にわたって重要なコマンドを紹介しましたがコマンドにはこれ以外にも色々なものがあります。また紹介したコマンドにも様々なオプションがあったりするので、興味を持ったかは調べてみてください。

絶対に覚えておいた方がいいターミナル(端末)のコマンドおよび使い方〜その2〜

その2ということで今回は実際によく使うターミナルコマンドの中でも他の操作で代替できなかったり、代替するのが面倒なコマンドを紹介したいと思います。

 

・cdコマンド

これはchange directoryの略でプログラミングをやったことある人なら誰でも使ったことがあるでしょう。

cd ..

とすれば一つ前の階層に

cd ~/

とすればホームディレクトリに戻ることができます。

この操作を他の操作で代替する場合はその1で紹介したようにFinderからターミナルを開けるようにしていた場合、Finderで階層を移動してからそこでファインダーを開くというものがありますが、明らかにこちらのコマンドを使った方が楽だと思います。

 

・lsコマンド

これはlistの略でカレントディレクトリ(現在いる階層)にあるファイルを表示してくれます。

ls -l

とすれば権限情報(そのファイルに対して可能な操作が何かを示す情報)などの詳しい情報が見れます。

ls -a

とすれば隠しファイル(.で始まるファイルで普通にFinderを開いただけでは見れないようなファイル)が見れます。

代替操作としてはFinderがあげられますが、ターミナル画面を開いている場合にはこちらの方がすぐできていいと思います。またls -lで見れる情報などはFinderからも情報をみるとすれば見れますが、lsを使うとまとめてみれる点が良いです。隠しファイルに関しても普通はFinderから見れないようにしているので、こちらで見るのが良いでしょう。

 

pwdコマンド

これはprint working directoryの略で現在いるディレクトリーを教えてくれるコマンドです。現在いるディレクトリーの情報をFinderから見ることも可能ですが、こちらの方が早いでしょう。プログラムに絶対パス(ファイルの住所のようなもの)を書きたいときなどに便利です。

 

・touchコマンド

これはどうしてこういう名前なのかわかりません。何かに触るんですかね?名前の由来はともかくこのコマンドは空のファイルを作るコマンドです。MacだとFinderから空のファイルを作れない (もしかしたらうまく設定したら作れるかもしれません)ので結構便利です。代替手段としてはエディターなどからファイルを作成するという方法があります。状況によって使い分けるのが良いでしょう。

 

・open

これはファイルを開くコマンドです。openの意味そのままですね。ファイルを開くのはFinderから普通にできますが、上で説明したtouchコマンドでファイルを作った後はそのままopenで作成したファイルを開けるので便利です。

 

history

これは歴史、つまりターミナルで過去に打ったコマンドの一覧を表示します。現れたコマンド一覧の横についた数字をnとすると

!n

と打ち込むことでそのコマンドを再び打てます。この操作は上ボタン(?)を何回も押して過去に遡るという方法でも代替でき、どれくらい過去のコマンドを再利用した以下によってどちらが楽かが変わると思います。

 

・clear

このコマンドを打つとターミナルで過去に実行してきたことが画面から消えます(良い説明が思いつかなくて説明下手でごめんなさい)。代替方法としてはターミナルを一旦閉じてもう一回開くという方法があります。このコマンドはエラーが長くてどこからが今回のコマンド実行によるエラーかがわかりづらいときなどに使うと良いと思います。

 

それぞれ細かいオプションは色々あるのですが、基本としてはこの辺りを覚えておけば良いと思います。