氣象報告常常不準

台湾生活。華語・台湾語学習。システム関連の話題など。

DelphiでAndroid開発挑戦日記(3)

(タイトル変えました!)

 RAD Studio XE5に含まれるDelphi起動して、ターゲットのAndroidデバイスを「デバッグモード」にしてUSB接続すれば、自動認識されて、それをターゲットにした開発ができるようになる。

 

 そのとおりでHTCのスマホはOKだった。だが、Sonyが以前出していたタブレット形端末(Sony Tablet S)をつないで見たら、認識してくれない。

 

 ソニーのサイトで見つけた「Android SDK開発環境設定について」

 http://www.sony.jp/support/tablet/products/info/sdk.html

 HTCと違って、一手間必要なんですね。使う立場では、「つなぐだけ」、にしてほしいところだ。「こんなことくらいできなくて、開発なんてできるのかー?」と言われたら返す言葉が無いが(汗)。

 

 さて、「SDK・USBドライバのインストール、および設定」をせよとあるが、RAD Studioのインストールでほとんど準備はできているのではないかな。

 SDKマネージャーを起動して開発環境を確認するが、

 RAD Studioの場合は

 スタート→すべてのプログラム→Embarcadero RAD Studio XE5→Android Tools

を開く。

Statusが UpdateAvailableになっているものが

(Tools)

Android SDK Tools (22.0.1→22.2.1)

Android SDK Platform-tools(17→18.0.1)

(Extrasの)

Android Support Library(13→18)

の3つ。

 

デフォルトでチェックがついていながら未インストールのものが

(Android4.3)

  Documentation for Android SDK

  SDK Platform

  Samples for SDK

  ARM EABI v7a System Image

  Intel x86 Atom System Image

  Google APIs

  Sources for Android SDK

(Extras)

 USBDriver

の8つ。

 

右下に「Install 11 packages」「Delete 3 packages」

というボタンが表示されているが。ご指名の(3+8)の11パッケージはぜんぶInstallしておく。

→インストール完了まで約40分かかった。

 

 RADStudioの環境のSDK Pathは

 C:\Users\Public\Documents\RAD Studio\12.0\PlatformSDKs\adt-bundle-windows-x86\20130522\sdk

Google USB Driver は extras\google\usb_driver

 C:\Users\Public\Documents\RAD Studio\12.0\PlatformSDKs\adt-bundle-windows-x86\20130522\sdk\extras\google\usb_driver

にある。そこ開いて、ソニーサイトで解説されている手順 

http://www.sony.jp/support/tablet/products/info/sdk.html

を実行した。

 「今度こそ」、といさんでソニータブレットS挿してみたがやはりまだ認識せず。PC再起動してつなぎなおしてみたが・・・

 

だめじゃん。お手上げ状態。

 =====================

検索してみたところ、

「be-style」様のブログ

http://blog.be-style.jpn.com/article/53114554.html

にて、この問題点と追加情報が詳しく解説されているのを見つけました。

 

 

※つまり、ソニーのサイトの記載だけでは情報不足だったということ。

 

「be-style」様が書かれている『追加』の手順どおりに作業して、ようやく当方でも、ソニータブレットSを認識しました。

f:id:liuk:20131001115953j:plain

 

 さあこれで、タブレット用アプリを!と試してみたのだが、なんだろこれ。SonyTablet本体にアプリの転送は出来た。しかし実行と同時に、作ったフォームを拝む前に終了して閉じてしまう。(HTCのスマホに戻したら、問題なく動いたが・・。)

DelphiでAndroid開発挑戦日記(2)

 前回、PCとUSB接続したAndroid端末をDelphiに認識させることができた。

さっそくこいつをターゲットにして、何か動かしてやろうとしたが、

エラー

プロセスを生成できません。

C:\...\Project1.apkをインストールできません。

Failure

[INSTALL_PARSE_FAILED_NO_CERTIFICATES]

となってしまった。アプリに署名が無いから、らしい。

 Delphiをいじっているうちに「構成」の設定を「アプリケーションストア」にしてしまっていたのが原因。「構成」を「デバッグ」に設定していれば、署名なしで配置でき、問題なく動作する。 

 「署名」については

http://docwiki.embarcadero.com/RADStudio/XE5/ja/%E7%BD%B2%E5%90%8D%E6%B8%88%E3%81%BF_Android_%E3%82%A2%E3%83%97%E3%83%AA%E3%82%B1%E3%83%BC%E3%82%B7%E3%83%A7%E3%83%B3%E3%81%AE%E9%85%8D%E7%BD%AE

に書いてあるが、作成したアプリを公開するのでなければ、(自分で使うだけのアプリなら)署名の事はとりあえず考えなくていい。

 これまで、恥ずかしながら、「開発環境の構築で四苦八苦して開発をはじめる前に力尽きる」なんてこともあったのだが、RadStudio XE5のDelphiについては、デフォルト設定でインストールして、『デバッグモードにしたAndroid端末』を開発PCにUSB接続すればすぐ使えるようになった。

 付属のサンプルコードに、GPSや加速度センサー等を活用する例があり、勉強になる。サンプルコードを実機で走らせてみるのは面白い。何気なく使っていたスマホが多機能なセンサーの塊である事を実感させられる。

 しばらくはサンプルコードを一つ一つ試しながら、遊んでみよう。ゲームなんかよりこのほうが面白いと思う。

DelphiでAndroid開発挑戦日記(1)

「RAD Studio XE5*1に含まれるDelphiで、Androidアプリの開発が出来るようになった」という点に魅力を感じて、(RAD Studio XE2からの)アップデートをした。

  

 自身、Android開発は初心者だが、Delphiは、先代のTurboPascal時代からお世話になっている。後者のノウハウを前者に活かせればよいなと期待はふくらむ。

 「ダウンロード版」を使っているが、インストールはだいぶ楽になった感じ。XE2のときは、なにかと途中でうまくいかないことがあって、結局「ISOイメージをDVD-Rに焼いて、そこからインストール」しないとならなかった。今回は、ダウンロードしたEXEファイルの実行だけで無事、最後まで行ってくれたし、Android開発に必要な、SDK NDK JDK関係もデフォルトで自動インストールしてくれた。

 但し、自分のPC(Core2 1.86GHz)では、二時間以上かかったように思う。インストールは時間に余裕があるときにやったほうがよさそうだ。(カタログには環境は「2GHz以上推奨」とある)

 

 

 Delphiを起動してみる。統合環境のぱっと見はXE2と同じようだ。この画面ならとっつきやすいのでありがたい。

 最初に表示される「ウェルカムページ」によると、アンドロイド開発を試したいとき、まず見るべきはこのビデオ(英語、5分弱)らしい。

http://www.youtube.com/watch?feature=player_embedded&v=8H80pEot4No

 

 見た感想。「USBで持っているAndroid端末つなげば、自動認識してくれるのでそれを『ターゲット』に設定すればチャチャチャのチャー!」ってことなのかな?

 

 エンバカデロ・デベロッパーTVのページ↓ から「RAD Studio XE5もっと見せます」のビデオを見る。こちらは日本語、32分。

http://www.embarcadero.com/jp/developers-tv

 

 

 8分40秒あたりに出てくるが「何も設定しなくてつなげば認識」してくれるらしい。

「では・・」と、自分の 「HTC One X+ (Android4.2.2)」を つないでみた。

 

・・・・認識しないじゃないの。

 

・開発者の方には当たり前なのかもしれないが、いろいろ検索してみると、こういうときは先に、スマホの方を、「デバッグモード」にする必要があるみたいだ。→そのためには、「開発者オプション」を表示する必要がある。

 

 そのやり方が、アンドロイド4.2以降の場合、不思議なおまじない!になっている。

参考)http://www.yahoo-help.jp/app/answers/detail/p/601/a_id/54447/~/usb%E3%83%87%E3%83%90%E3%83%83%E3%82%B0%E3%82%92%E6%9C%89%E5%8A%B9%E3%81%AB%E3%81%99%E3%82%8B%E3%80%81%E6%8F%90%E4%BE%9B%E5%85%83%E4%B8%8D%E6%98%8E%E3%82%A2%E3%83%97%E3%83%AA%E3%81%AE%E3%82%A4%E3%83%B3%E3%82%B9%E3%83%88%E3%83%BC%E3%83%AB%E3%82%92%E8%A8%B1%E5%8F%AF%E3%81%99%E3%82%8B#1

「設定」「バージョン情報」「ソフトウェア情報」「その他」へ入って、「ビルド番号」を7回選択する。すると開発者向けオプションが表示されるとのこと↑。

 途中で、「あと3ステップで」「あと2ステップで」などと表示されたが、なぜか最後に「お客様はデベロッパーではありませんね」と表示された。ムカッ。

 一度抜けてから、「設定」「バージョン情報」「ソフトウェア情報」「その他」へ入って、再度「ビルド番号」を触ると、「必要ありません、お客様はデベロッパーです」と表示。よくわからん。

 

 この後、調べたが、一度「開発者オプション」を表示させてしまうと、簡単には消せないみたい↓ 

参) Android 4.2の「開発者向けオプション」を削除する方法↓

http://andbrowser.com/development/1246/how-to-remove-developer-options-for-android-4-2/

 なんで「デベロッパーではありませんね」と表示されたのか、再現テストもできないまま、ともかくUSBデバッグモードをオンに。

 Delphiを起動して、スマホを接続。しばらく待ってようやく「プロジェクトマネージャー」の「ターゲット」に「HTC One X+」が追加されました。

 

 ようやく最初の関門を突破、といったところでしょうか。(続く、かも)

*1:RAD Studioはエンバカデロ社の開発ツール製品

 http://www.embarcadero.com/jp/products/rad-studio

結城先生のクロッシング問題、復習メモ(Delphi)

 > 挑戦者求む!交差点をすばやく数えよう! by The Essence of Programming http://t.co/2Xn4WbblEf @codeiqさんから

 

・「三十万個超の数値データを順々に読み出す、一つの数値を読み出すたび、『それより大きい既出の数値の個数』を積算していく」問題だと解釈。

 

 

 そこで、自分はDelphiで「既出の数値をリスト構造に昇順で保存する」という方法をとったが、9秒が限界。課題要件の「3秒未満」には至らなかった。

 

 9/3にいただいた結城先生の解説「マージソート版」は「あ、これだったのかぁ」という印象だったが、別解の「逆転表版」は目からうろこ。模範プログラム例はRubyとC。これをDelphiに移植して、「本当に(Delphiでも)1秒以下で正解が出せる」ことに、まず感激。

 ただ、「何でこのソースコードで、正解が出るのか」なかなかピンとこなかった。変数の動きを追いかけ追いかけ、ようやく、「上位ビットを配列の添字にしている」ことで「上位ビットが共通のデータ」をまとめて扱えていることを理解。

 なるほど、無駄が無く美しい。

ーーーーーーーーーーーーー

しばらくすると忘れそうなのでDelphi移植版に、いろいろコメントつけたのを置いておく。(フォームに出力用メモコンポーネントMemo1を置いている。)

procedure TForm1.Button1Click(Sender: TObject);
//逆転表版
var
    bits, i,j,k,s, datacount: Integer;
    cross_sum   : UINT64;
    nums : TList<Integer>; //課題の配列を入れておく
    invs : TList<Integer>; //逆転表用

    StringList:  TStringList; //ファイル読み出し用文字列リスト

begin
    Memo1.Lines.Add(DateTimeToStr(Now));//開始時刻記録

    cross_sum := 0;  //クロス数初期化

    //課題のデータを文字列リストに読み出し

    StringList := TStringList.Create;
    StringList.LoadFromFile('C:\temp\crossing.txt'); //ファイル置き場指定し読み出し

    //データ数 (=314159個)が求まる↓
    datacount := StringList.Count;

    //作業用配列準備
    nums := TList<Integer>.Create;
    invs := TList<Integer>.Create;
    try
      for i := 0 to datacount -1 do begin
        nums.Add(StrToInt(StringList.Strings[I])); //文字列リストから数値リストへ変換
        invs.Add(0);//ゼロ埋め(メモリ確保)
      end;

      //配列の添え字を2進表記した場合の最上位ビットの桁位置をbitsへ。
      //配列要素数314159個だが 2^19で524288, 2^18で262144なのでbitsは18 になる
      for bits := 31 downto 1 do begin
        if (datacount and (1 shl bits))>0 then break;
      end;

      //上位ビットから順に処理。
      for k := bits downto 0 do begin
        //使う分だけ、invsの初期化
        for s := 0 to datacount div (1 shl (k+1)) do invs[s] := 0;

        //横、データ数の分だけスキャン
        for j := 0 to datacount-1 do begin
          s := nums[j] div (1 shl (k+1));//データの上位のビットだけ取り出す


          if nums[j] and (1 shl k)>0 then  invs[s] := invs[s]+1
          //↑そのビットが1のとき、
          //『上位ビットが共通で、その時点で初めて自分より大きいとわかる

    //自分よりも左にある数の個数』はゼロ。
          //上位ビット(s)が共通で、そのビットが1である個数:invs[s]を

    //インクリメントしておく

          else cross_sum := cross_sum + invs[s];
          //↑そのビットが0のとき、
          //『上位ビットが共通で、その時点で初めて自分より大きいとわかる

    //自分よりも左にある数の個数』は
          //その時点でのinvs[s]であるから、それをクロス数に追加。

        end;
      end;
      Memo1.Lines.Add(IntToStr(cross_sum));//結果の出力
    finally
      invs.Free;
      nums.Free;

      StringList.Free;
    end;
    Memo1.Lines.Add(DateTimeToStr(Now));//終了時刻記録
end;

=============

出力結果(処理時間一秒未満)

2013/09/05 15:21:01
24689222839
2013/09/05 15:21:01

防災の日(ほんとにあった怖いデータベース)

 9・1なので防災について考えてみる。頭に浮かぶのは、遠い過去に見た、とても怖い「災害時安否確認Webデータベース」。今でも思い出すと寒気がする↓

 

 Webで入力する項目がいくつかある。
・安否「無事です」とか「怪我しています」とか。
・場所「○○にいます」「××で待つ」とか。
・その他コメント、など入力して「確定」すると記録されて、家族・関係者等と安否情報共有ができる、というものだ。

 ここまではよい。

 

 ※問題は、入力後、情報を追加したいときに、どうなるか?

 どうなるかというと、「全部まっさら」になる。!

 そう。まっさら。・・・・何を言っているかって?

ーーーーーーーーーーーーーー

 たとえば、「安否」、「場所」、「コメント」、その他もろもろの項目一つ一つを、入力して確定したとする。

 その後、状況が変わった(避難場所が変わった)ので「場所」だけ変更したいとする。

 安否、場所、コメント、その他項目全てが全部空欄の入力画面が出る。

 「場所」の項目に新しい情報を入力し「確定」をクリックする。

 すると「上書き」されてしまう。「追記」ではない。「上書き」。しかも「全項目上書き」だ。

 場所の情報を変えただけのつもりが、最初に入力した「安否」も「コメント」も、その他もろもろの項目も、一切残らない。履歴としての記録もされていない。

ーーーーーーーーーーーーーー

 そんなものにどれだけコストをかけていたのか。「情報の扱い方」の基本が「全くわかっていない」業者にでも作らせたのだろうか。

 

台湾の医療費

 台湾の医療費(健保)、不思議だ。通っているクリニックでは、『受診前』に200元(約650円)前払いしたら終わり。その後、採血検査等をしても追加料金は発生しない。

 薬代も不思議。

 同じ薬なのに、前々回は、2週間分で10元。

 「ずいぶん安いね?」と聞いたら、「健保があるからね!」みたいな事を言われた。

 

 前回は1箇月分で30元。(比例しないのか?)

 

 今日は、医師から3箇月分の処方箋をまとめてもらった。ただし、薬局で渡されるのは1箇月分までで、あとは毎月薬局にとりにいく方式。

 薬代を聞いたら、「要りません。」という。「健保があるからね!」みたいな事を言われた(?)。

 

 お試し期間(副作用チェック中)だけ、薬代が要る(?)のかなぁ。その辺、納得できるくらいまで聞きだせる会話力はまだ無い。

 

待ち方(締め切り過ぎて思い出した怖いコード)

納涼!ほんとにあった怖いコード(by CodeIQ×はてな)

↑の締め切りは過ぎてしまったので、これはもう応募対象にはならないが、一つ思い出した怖いコードの紹介を。

 

N88BASICの頃は、「ちょっと待機」というとき、

10 FOR I=1 TO 10000:NEXT I

みたいな書き方がしばしばされていた。

 

・時代は下ってWindowsになっても、しばらく装置制御関係では、「もとN88BASICのソースコード」を強引に移植したようなコードがかなりあった。

 ループ回数を増やしたり、ループ内に重い処理を置いたりという『工夫(?)』はあるが、本質は変わらない。「待つ」べきところに来ると一定時間「ハングアップ」したように、マウスもキーも受け付けなくなる。

 そんなコードにしばしば出くわした。あちらこちらにあった。

 たまに見かけたコードの「待ち」のループ内に、DoEvents(VB)とかApplication.ProcessMessages(Delphi) とか使ってあるだけで、当時は「とても素敵」に思えたものだ。

 

 ※でも、「待ち」の処理にForループってのは、流石に今はもうやめてもらわないと。