2014年9月23日火曜日

PHPmemo_day4

PHPの基本に関するメモ。参考にしているのはPHPによるWebアプリケーションスーパーサンプル第2版の第4章(文字列)です。

  • 文字列の結合と代入を一度に行うための演算子は.=である
  • substr関数は部分文字列を抽出するための関数である。
  • $s = "0123456789";
    substr($s, 5); // "56789"になる。添字で5以降が抽出される。
    substr($s, -2); // "89"になる。最後の2文字を抽出する。
    substr($s, 0, 2); // "01"になる。添字で0から1までが抽出される。
  • substr関数はマルチバイト文字に対して使うべきではない。マルチバイト文字に対応するmb_substr関数を使うべきである。mb_substr関数では読み込む文字のコードを指定することができる。
  • str_shuffle関数で文字列をランダムに並び替えることができる。
  • str_replace関数は処理対象の文字列、置換対象の文字列、置換後の文字列を指定することで、返り値で処理対象後の文字列が得られる。PHP5では第4引数に変数を与えると、置換した回数が返される。
  • ereg_replace関数は正規表現パターンを利用して文字列を置換できる。
  • $s = "012-abc";
    $p = "[0-9]";
    $r = "*";
    echo ereg_replace($p, $r, $s); // "***-abc"に置換される
  • preg_replace_callback関数を用いると、パターンにマッチした部分をどのように置換するかを関数で定義できるようになる。callbackなので、指定したパターンが見つかる度に指定した関数が呼ばれることになる。
  • 文字列の前後の空白を取り除くにはtrim関数を用いる
  • 文字列の比較にはstrcmp関数を用いる。大文字小文字を区別せず比較するのであれば、strcasecmp関数を用いればよい。
  • strtoupper、strtolower関数により、文字列をすべて大文字、小文字に変換することができる。
  • ucfirst、ucwords関数を用いると、文字列の文章の先頭、文字列の各単語の先頭を大文字に変換することができる。
  • explode関数は指定した文字で文字列を分割する。返り値はarrayになる。
  • n文字ごとに文字列を分割したいということであれば、str_split関数を用いればよい。
  • 文字列を繰り返し結合するにはstr_repeat関数がある。
  • 文字列中に特定の文字列が出現する回数を求める関数として、substr_count関数がある。
  • strlen関数はバイト単位の文字列の長さを返す。従って、ひらがなは2バイトなので2文字としてカウントされる。ひらがらのようなマルチバイト文字を1文字としてカウントするのはmb_strlen関数である。
  • mb_convert_kana関数を用いると全角と半角間の変換ができる。日本語限定と思って使うこと。

2014年9月20日土曜日

PHPmemo_day3

PHPの基本に関するメモ。参考にしているのはPHPによるWebアプリケーションスーパーサンプル第2版の第3章(変数、定数)です。

  • echoで文字列と変数の間にスペースを入れずに出すには{$var}のように{}で囲えばよい
  • 変数の型を調べるにはgettype関数を利用する
  • 変数の型変換にはsettype関数を利用する
  • var_dump関数を利用すると、変数の方に関する情報と値をまとめて出力できる
  • get_defined_vars関数を利用すると定義済みの変数情報一覧を取得できる。
  • define関数で定数を定義できる。C言語の#defineみたいなものとみてよいだろう。
  • defined関数で定数が定義済みか調べられる。
  • define("EXP", 2.718)のように定義したEXPを参照するにはEXP、あるいはconstant("EXP")とする。
  • __FILE__はPHPコードの書かれたファイル名、__LINE__はコードの行番号を表す定数である。
  • M_PIは円周率、M_SQRT2はルート2を表す定数である。
  • get_defined_constants関数で定義済みの定数一覧を取得できる。
  • get_defined_constants関数のように一覧を取得して表示したいのであれば、print_r関数が使える。print_r関数はデバッグにも使える。
  • $_SERVER["HTTP_USER_AGENT"]はブラウザの情報を、$_SERVER["HTTP_REFERER"]はリンク元を、$_SERVER["REMOTE_ADDR"]はアクセス元のIPアドレスを表す(PHP4.2.0以降)

2014年9月18日木曜日

PHPmemo_day2

PHPの基本に関するメモ。参考にしているのはPHPによるWebアプリケーションスーパーサンプル第2版の第2章前半です。 コードを書いて紹介するのは大変なので、C言語やJavaと違うところを主に取り上げていきます。

  • フォームからPOST送信された値を受け取るときには$_POST["content"]とすればnameがcontentのデータを受け取れる。
  • php.iniのregister_globalsをONにすると$contentで参照できるようになるが、セキュリティの都合上OFFにするのが一般的
  • @$_POST["content"]とすることで、contentが初期状態で何も設定されていない状態でもエラーが出なくなる
  • $_SERVER["PHP_SELF"]は現在表示中のURLを表すサーバ変数である
  • $HTTP_POST_VARS["content"]のようにPOST送信されたデータを受け取ることもできるが、php.ini-recommendedでは無効になっている。
  • php.iniにはdisplay_errorsという設定項目がある。これはエラーを画面に出すためのオプションであり、デバッグに使える。
  • $_GET["type"]などとすればGET送信されたURLのtype=の値を取得することができる。
  • フォームから送信されるデータはstring型である。
  • フォームから変数を受け取って、同じ変数名に受け取った値を設定するには、extract関数を使う。ただし、extract($_POST)のように記述すると、ユーザの入力をそのまま出すのでエスケープ処理などをした方がよいとされる。
  • フォームからある変数が飛んできているか調べるにはisset関数を利用する。if文や三項演算子を用いて変数の有無で変数を設定する際に使える。
フォームからの入力内容を確認するためによく使われる関数についても紹介しておきます。
  • function_exists
    • 引数の文字列の関数名が定義されているかを調べるための関数
  • strlen
    • 文字列の長さを調べるための関数
  • empty
    • 空、または0でTRUEを返す関数
  • isset
    • 変数が定義されていればTRUEを返す関数
  • stristr、strstr
    • 文字列のマッチングで利用する関数。前者は大文字と小文字の違いをignore(無視)するが、後者では区別している。
  • is_numeric
    • 文字列が数字として解釈できるのであればTRUEを返す関数。数字は半角でないとTRUEにならない。
  • ctype_digit
    • is_numericに似ているが、小数点が含まれるとFALSEになる点が異なる。あとは同じ。
  • ctype_loert、ctype_upper
    • 引数の文字列が小文字、あるいは大文字だけからなるかを調べる関数
  • checkdate
    • 引数で与えた月、日、年の数値がグレゴリオ暦で正しい日付か(存在する日付であるか)調べる関数

2014年9月17日水曜日

PHPmemo_day1

PHPの基本に関するメモ。参考にしているのはPHPによるWebアプリケーションスーパーサンプル第2版の第1章です。 コードを書いて紹介するのは大変なので、C言語やJavaと違うところを主に取り上げていきます。

  • PHPのコードは<?~?>で囲う
  • 変数は$i=(値)のように定義する
  • echo、printで文字列出力を行う。HTMLをechoで出力する方法もある。
  • echoをダブルクォートで囲うと変数は変数の値に解釈され、シングルクォートで囲うと変数名は文字列と解釈される
  • $s = "abc";
    echo "string=$s"; // string=abcと表示される
    echo 'string=$s'; // string=$sと表示される
  • 文字列の結合はドット(.)で行う
  • 空文字、null、0も論理値のFALSEとして扱われる。それ以外はTRUEになる。
  • 関数にはデフォルト値を設定することができる。
  • func(1)とcall_user_func(func, 1)は同値になる

2014年8月17日日曜日

TopCoder SRM487 Div2 250Pts

このTopCoderの問題はこちらで見ることができる(要TopCoder登録 & 問題文は英語)。問題文についておおまかに説明する。

ウサギたちはプログラミングは好きだが、プログラミングの試験が好きではない。黒、グレー、白の3匹のウサギは最終試験を終えた。ウサギたちが問題について議論している間に、教授がやってきて、"黒いやつ、お前は0点だ、知識を確かなものにするために、グレーと白が取った点数の最大値の合計点を計算するプログラムを書け"といった。

試験はN問からなるものであった。ウサギたちは同じ問題を提示される。各問題に対し、その答えとしてA~Zのアルファベットの大文字を書かなければならなかった。問題に対し、1つの文字のみが正しいものとされ、他の25文字は正しくない回答となっている。正解は1点となり、ウサギの得た点数は問題に正解した数に一致する。

black、gray、whiteという黒、グレー、白のウサギが書いた回答を表す文字列が与えられる。それぞれの文字列はN文字からなり、文字列のi番目の文字はそれぞれのウサギのi番目の回答を表すものとする。黒ウサギの点数が0のときに、グレーと白のウサギが獲得しうる点数の合計の最大値を返せ。

私の回答は以下の通り。

public class BunnyExamAfter {

 public int getMaximum(String black, String gray, String white) {

  int points = 0;
  for( int i=0 ; i<black.length() ; i++ ){
   if( black.charAt(i) == gray.charAt(i) &&
    black.charAt(i) == white.charAt(i) ){
    // pass
   }else if( black.charAt(i) != gray.charAt(i) &&
     black.charAt(i) == white.charAt(i) ){
    points++;
   }else if( black.charAt(i) == gray.charAt(i) &&
     black.charAt(i) != white.charAt(i) ){
    points++;
   }else if( black.charAt(i) != gray.charAt(i) &&
     black.charAt(i) != white.charAt(i) &&
     gray.charAt(i) == white.charAt(i) ){
    points += 2;
   }else if( black.charAt(i) != gray.charAt(i) &&
     gray.charAt(i) != white.charAt(i) ){
    points++;
   }
  }
  return points;
 }

}

得点は220.72/250、1回のsubmitでシステムテストクリア。

2014年8月6日水曜日

TopCoder SRM486 Div2 250Pts

このTopCoderの問題はこちらで見ることができる(要TopCoder登録 & 問題文は英語)。問題文についておおまかに説明する。

奇妙な省略形が扱いにくい携帯機器でテキストを書くのにしばしば用いられる。アルファベットと空白からなるテキストをエンコードする方法の1つに次のものがある。

  • 空白はそのままで、各単語は単語ごとにエンコードされる。ここで単語とはアルファベットの続く連続した文字列をいう。
  • もし単語が母音のみからなる場合、それはそのまま書かれる。
  • もし単語が1つ以上の子音を含むのであれば、直前に別の子音がない子音のみ書く。母音を買い手はならない。
  • 上記の規則において、母音は'a', 'e', 'i', 'o'と'u'である。他の文字は子音と考える。

例えば、"ps i love u"というのは、"p i lv u"と省略され、一方、"please please me"は"ps ps m"と略されるであろう。 originalという文字列が引数で与えられたとき、先述の方法で省略されたメッセージを返すメソッドを作成せよ。

私の解答は以下の通り。

public class TxMsg {

 public String getMessage(String original) {
  StringBuilder msg = new StringBuilder("");
  String[] strs = original.split(" ");
  for( int i=0 ; i<strs.length ; i++){
   if( isAllVowel(strs[i]) ){
    msg.append(strs[i] + " ");
   }else{
    msg.append(makeEncodedMessage(strs[i]) + " ");
   }
  }
  // if文の後者により、最後に空白ができる可能性があるので、trimを行う
  return msg.toString().trim();
 }

 private static boolean isAllVowel(String s){ // 入力がすべて母音か判断
  char[] vowels = {'a', 'e', 'i', 'o', 'u'};
  for( int i=0 ; i<s.length() ; i++ ){
   boolean isvowel = false;
   for( int j=0 ; j<vowels.length ; j++ ){
    if( s.charAt(i) == vowels[j] ){
     isvowel = true;
     break;
    }
   }
   if( ! isvowel ) return false;
  }
  return true;
 }

 private static String makeEncodedMessage(String s){
  char[] vowels = {'a', 'e', 'i', 'o', 'u'};
  StringBuilder sb = new StringBuilder();
  boolean prevConsonant = false;
  boolean currentConsonant = true;

  for( int i=0 ; i<s.length() ; i++ ){
   currentConsonant = true;
   for( int j=0 ; j<vowels.length ; j++ ){
    if( s.charAt(i) == vowels[j] ){
     currentConsonant = false;
     break;
    }
   }
   if( !prevConsonant && currentConsonant ){
    sb.append(s.charAt(i));
   }
   prevConsonant = currentConsonant;
  }
  return sb.toString();
 }

}

得点は158.01/250、1回のsubmitでシステムテストクリア。

2014年7月30日水曜日

Raspberry PIでSSHの初期設定時に発生したエラーを回復する方法

Raspberry PIの初期設定中に、「Initial ssh key generation still running. Please wait and try again.」 というメッセージが出てきて困ったことがありました。何が原因で発生したのかよく分からないのですが、 最初の起動時に接触が悪かったのため、一度設定前に電源を落とすなどしたことが可能性として考えられました。 さて、この状態になった場合、次の鍵を作り直すためのコマンドを入力することによってSSHが使えるようになります。

作業時には初期状態(User:pi、Password:Raspberry)のアカウントを利用しました。なのでsudoでコマンドが実行ができます。

# rm /var/log/regen_ssh_keys.log
# sudo rm /etc/ssh/ssh_host*
# sudo ssh-keygen -A

個人的にはログを消すとうまく動作するというのはあまり納得できません。 logではなくlockという拡張子のファイルを削除するのであれば理解できるのですが。

フォロワー

ページビューの合計