/* * PROJECT: NyARToolkitAS3 * -------------------------------------------------------------------------------- * This work is based on the original ARToolKit developed by * Hirokazu Kato * Mark Billinghurst * HITLab, University of Washington, Seattle * http://www.hitl.washington.edu/artoolkit/ * * The NyARToolkitAS3 is AS3 edition ARToolKit class library. * Copyright (C)2010 Ryo Iizuka * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . * * For further information please contact. * http://nyatla.jp/nyatoolkit/ * or * */ package jp.nyatla.nyartoolkit.as3.core { import jp.nyatla.nyartoolkit.as3.core.analyzer.histogram.*; import jp.nyatla.nyartoolkit.as3.utils.as3.*; import jp.nyatla.nyartoolkit.as3.*; /** * ARMat構造体に対応するクラス typedef struct { double *m; int row; int clm; }ARMat; * */ public class NyARMat { /** * 配列サイズと行列サイズは必ずしも一致しないことに注意 返された配列のサイズを行列の大きさとして使わないこと! * */ protected var m:Vector.>; private var __matrixSelfInv_nos:Vector.; private var clm:int; private var row:int; public function NyARMat(i_row:int,i_clm:int) { this.m = ArrayUtils.create2dNumber(i_row, i_clm); this.__matrixSelfInv_nos=new Vector.(i_row); this.clm = i_clm; this.row = i_row; return; } /** * 行列の列数を返します。 * @return */ public function getClm():int { return clm; } /** * 行列の行数を返します。 * @return */ public function getRow():int { return row; } public function getArray():Vector.> { return this.m; } /** * 逆行列を計算して、thisへ格納します。 * @throws NyARException */ public function matrixSelfInv():Boolean { var ap:Vector.> = this.m; var dimen:int = this.row; var dimen_1:int = dimen - 1; var ap_n:Vector., ap_ip:Vector., ap_i:Vector.;// wap; var j:int, ip:int, nwork:int; var nos:Vector. = this.__matrixSelfInv_nos;//ワーク変数 // double epsl; var p:Number, pbuf:Number, work:Number; /* check size */ switch (dimen) { case 0: throw new NyARException(); case 1: ap[0][0] = 1.0 / ap[0][0];// *ap = 1.0 / (*ap); return true;/* 1 dimension */ } var n:int; for (n = 0; n < dimen; n++) { nos[n] = n; } /* * nyatla memo ipが定まらないで計算が行われる場合があるので挿入。 ループ内で0初期化していいかが判らない。 */ ip = 0; // For順変更禁止 for (n = 0; n < dimen; n++) { ap_n = ap[n];// wcp = ap + n * rowa; p = 0.0; for (var i:int = n; i < dimen; i++) { if (p < (pbuf = Math.abs(ap[i][0]))) { p = pbuf; ip = i; } } // if (p <= matrixSelfInv_epsl){ if (p == 0.0) { return false; // throw new NyARException(); } nwork = nos[ip]; nos[ip] = nos[n]; nos[n] = nwork; ap_ip = ap[ip]; for (j = 0; j < dimen; j++) {// for(j = 0, wap = ap + ip * rowa, // wbp = wcp; j < dimen ; j++) { work = ap_ip[j]; // work = *wap; ap_ip[j] = ap_n[j]; ap_n[j] = work; } work = ap_n[0]; for (j = 0; j < dimen_1; j++) { ap_n[j] = ap_n[j + 1] / work;// *wap = *(wap + 1) / work; } ap_n[j] = 1.0 / work;// *wap = 1.0 / work; for (i = 0; i < dimen; i++) { if (i != n) { ap_i = ap[i];// wap = ap + i * rowa; work = ap_i[0]; for (j = 0; j < dimen_1; j++) {// for(j = 1, wbp = wcp,work = *wap;j < dimen ;j++, wap++, wbp++) ap_i[j] = ap_i[j + 1] - work * ap_n[j];// wap = *(wap +1) - work *(*wbp); } ap_i[j] = -work * ap_n[j];// *wap = -work * (*wbp); } } } for (n = 0; n < dimen; n++) { for (j = n; j < dimen; j++) { if (nos[j] == n) { break; } } nos[j] = nos[n]; for (i = 0; i < dimen; i++) { ap_i = ap[i]; work = ap_i[j];// work = *wap; ap_i[j] = ap_i[n];// *wap = *wbp; ap_i[n] = work;// *wbp = work; } } return true; } // *************************************** // There are not used by NyARToolKit. // *************************************** // public function realloc(i_row:int,i_clm:int):void // public function matrixMul(i_mat_a:NyARMat,i_mat_b:NyARMat):void // public function zeroClear():void // public function copyFrom(NyARMat i_copy_from):void // public static function matrixTrans(dest:NyARMat,source:NyARMat):void // public static function matrixUnit(uint:NyARMat):void // public function matrixDup(i_source:NyARMat):void // public function matrixAllocDup():NyARMat // private static const PCA_EPS:Number = 1e-6; // #define EPS 1e-6 // private static const PCA_MAX_ITER:int = 100; // #define MAX_ITER 100 // private static const PCA_VZERO:Number = 1e-16; // #define VZERO 1e-16 // private function PCA_EX(mean:NyARVec):void // private static function PCA_CENTER(inout:NyARMat,mean:NyARMat):void // private static function PCA_x_by_xt(input:NyARMat,output:NyARMat):void // private static function PCA_xt_by_x(input:NyARMat,i_output:NyARMat):void // private var wk_PCA_QRM_ev:NyARVec = new NyARVec(1); // private function PCA_QRM(dv:NyARVec):void // private function flipRow(i_row_1:int,i_row_2:int):void // private static function PCA_EV_create(input:NyARMat,u:NyARMat,output:NyARMat,ev:NyARVec):void // private function PCA_PCA(o_output:NyARMat,o_ev:NyARVec):void // public function pca(o_evec:NyARMat, o_ev:NyARVec, o_mean:NyARVec):void // private var wk_vecTridiagonalize_vec:NyARVec = new NyARVec(0); // private var wk_vecTridiagonalize_vec2:NyARVec = new NyARVec(0); // private function vecTridiagonalize(d:NyARVec,e:NyARVec,i_e_start:int):void } }