2017-04-08 208 views
-2

你好,我想問關於二維數組中的比較問題。 我有以下2d數組與每個行中的雙參數。 我想比較第5行(即:期間0)與第5行(即:期間1) 我想比較 比較將逐行作爲1d數組我需要兩個1 d數組來比較彼此。Java二維數組比較

示例;

週期0(行0)與期間1(行0,ROW1,ROW2,ROW3,ROW4)

週期0行1對週期1(行0,ROW1,ROW2,ROW3,ROW4)

週期0行2比周期1(行0,ROW1,ROW2,ROW3,ROW4)

週期0行3比周期1(行0,ROW1,ROW2,ROW3,ROW4)

週期0第4行vs第1期(第0行,第1行,第2行,第3行,第4行)


然後

時期1行0對時間段2(行0,ROW1,ROW2,ROW3,ROW4)

時期1行1對週期2(行0,ROW1,ROW2,ROW3,ROW4 )

時期1行2比期間2(行0,ROW1,ROW2,ROW3,ROW4)

時期1行3比期間2(行0,ROW1,ROW2,ROW3,ROW4)

期間1行4與期間2(行0,行1,行2,行3,行4)


然後

時期2行0對週期3(行0,ROW1,ROW2,ROW3,ROW4)

時期2行1對週期3(行0,ROW1,ROW2, ROW3,ROW4)

時期2行2比周期3(行0,ROW1,ROW2,ROW3,ROW4)

期間2行3比周期3(行0,ROW1,ROW2,ROW3,ROW4)

時期2行4對週期3(行0,ROW1,ROW2,ROW3,ROW4)


我的目標是獲得期0的第一行,然後將其轉換爲一維數組,然後採取的第一行Period1然後將其轉換爲1d陣列等。

2d陣列如下;

雙[] [] = myDistributions新雙[] [] {

 row0 {0.15250886479593964,0.2610516793197853,0.11441768814194446,0.1265241345428162,0.3454976331995246}, 
     row1 {0.14389124837314887,0.10513281153155449,0.1833462741873425,0.36788054102686596,0.1997491248810186}, 
Period0 row2 {0.1111207312911868,0.17499901413730568,0.2914581757577288,0.20433331657432438,0.2180887622394655}, 
     row3 {0.0948730457966342,0.19288720600625753,0.19471332499886804,0.18018001280247228,0.3373464103957629}, 
     row4 {0.18877271931210932,0.26521449714587747,0.13230019262559328,0.27631809895720494,0.13739449195931552}, 

     row0 {0.1274517393962726,0.10526928843184565,0.35751329613481436,0.12240396832200726,0.2873617077151316}, 
     row1 {0.3016290729137225,0.09902028076323677,0.17515717333485062,0.35620664945852193,0.06798682352968743}, 
Period1 row2 {0.0948730457966342,0.19288720600625753,0.19471332499886804,0.18018001280247228,0.3373464103957629}, 
     row3 {0.18877271931210932,0.26521449714587747,0.13230019262559328,0.27631809895720494,0.13739449195931552}, 
     row4 {0.17804585265772793,0.25651982583759037,0.3860867129515085,0.09453797159458521,0.08480963695844175}, 

     row0 {0.2311120677942418,0.07901250493611567,0.15795189397863776,0.24546018732208122,0.28646334596884354}, 
     row1 {0.08823944830766299,0.26313933789756516,0.10406419933285384,0.3365866979847223,0.20797031647719286}, 
Period2 row2 {0.1274517393962726,0.10526928843184565,0.35751329613481436,0.12240396832200726,0.2873617077151316}, 
     row3 {0.3016290729137225,0.09902028076323677,0.17515717333485062,0.35620664945852193,0.06798682352968743}, 
     row4 {0.11962680738039468,0.1590225091909952,0.24009305610431117,0.11189649648370673,0.36936113084052996}, 

     row0 {0.17804585265772793,0.25651982583759037,0.3860867129515085,0.09453797159458521,0.08480963695844175}, 
     row1 {0.08823944830766299,0.26313933789756516,0.10406419933285384,0.3365866979847223,0.20797031647719286}, 
Period3 row2 {0.1274517393962726,0.10526928843184565,0.35751329613481436,0.12240396832200726,0.2873617077151316}, 
     row3 {0.0948730457966342,0.19288720600625753,0.19471332499886804,0.18018001280247228,0.3373464103957629}, 
     row4 {0.3962773409768214,0.12002724792315751,0.15722439889764284,0.11854502459707339,0.20792598760527947}}; 
+0

我不太明白你想如何比較每一行。 –

+0

你試圖達到什麼樣的比較(等於,大於,小於,在範圍內,全部)? – DevilsHnd

+0

感謝您的回覆Jacob G.,我認爲前5行是我的期間0然後第二個5行是我的期間1,然後第三個5行是我的期間2,並保持5行是我的期間3我有一個函數獲取2 1d數組作爲輸入。所以,首先我的函數輸入將是(週期0行0)和(週期1行0) – mstfky

回答

1

現在你已經對你評論之一中提到的幾乎你在做什麼,我們可以排序明白你試圖在這裏完成的。坦率地說,並沒有任何不尊重,你的解釋吸吮。 :P

我收集它的方式是嘗試從兩個特定的二維(2D)雙類型數組中取得行,並從這些雙重類型數據的特定行中檢索一個發散值。你當然還沒有透露過這種類型,如果你正在做這樣的分歧,我將不得不假設它是一個Kullback–Leibler Divergence。無論採用哪種方式,您都可以採用下面提供的代碼並對其進行修改,以調用您希望收集所需分歧的任何Java方法。

爲了完成這項任務,我們需要一些特定的方法,其中最重要的方法是爲我們提供分歧的方法。我在下面提供的方法就是這樣做的,前一段時間我寫的是Charles Sutton來自Univ。馬薩諸塞州阿默斯特計算機科學部該方法是「馬勒特」(MAchine Learning for LanguagE Toolkit)的一部分。這裏是Mr. Sutton's Divergence method這是開放源代碼:

/** 
* Returns the Kullback–Leibler (KL) Divergence, K(p1 || p2). 
* 
* The log is w.r.t. base 2. <p> 
* 
* *Note*: If any value in <tt>p2</tt> is <tt>0.0</tt> then the KL-divergence 
* is <tt>infinite</tt>. Limin changes it to zero instead of infinite. 
* 
*/ 
public static double klDivergence(double[] p1, double[] p2) { 
    double log2 = Math.log(2); 
    double klDiv = 0.0; 

    for (int i = 0; i < p1.length; ++i) { 
     if (p1[i] == 0) { continue; } 
     if (p2[i] == 0.0) { continue; } // Limin 

     klDiv += p1[i] * Math.log(p1[i]/p2[i]); 
    } 

    return klDiv/log2; // moved this division out of the loop -DM 
} 

對於我們的未來,我們需要一種方法來把兩個提供的2D double類型數組和提取數據的每行了出來,以獲取來自這兩個發散方法具體的行,無論他們是誰。我提供的方法如下(kldFromDoubleArrays())執行此操作。它是儘可能的基礎,因此會很容易遵循:

/** 
* This method will take each row from the supplied 2D double type array1 and 
* each row from the supplied 2D double type array2 and display the 
* Kullback–Leibler Divergence for each of those rows of data processed.<br><br> 
* 
* Note: This method outputs its results into the Console Window.<br><br> 
* 
* Note: This method utilizes <b>Charles Sutton's</b> method named klDivergence() to 
* acquire Kullback–Leibler Divergence values.<br><br> 
* 
* @param array1 (2D Double Type Array)<br> 
* 
* @param nameForArray1 (String) The string name to use for array1 for console 
* display purposes.<br> 
* 
* @param array2 (2D Double Type Array)<br> 
* 
* @param nameForArray2 (String) The string name to use for array2 for console 
* display purposes. 
*/ 
private void kldFromDoubleArrays(double[][] array1, String nameForArray1, 
     double[][] array2, String nameForArray2) { 
    //Iterate through Rows of array1... 
    for (int i = 0; i < array1.length; i++) { 
     //Declare a 1D Array to hold current row from array1 
     double[] p0 = new double [array1[i].length]; 

     //Iterate through Columns of current array1 Row... 
     for (int j = 0; j < array1[i].length; j++) { 
      //Place current array1 row into a 1D Array p0 
      p0[j] = array1[i][j]; 

      //Iterate through Rows of array2... 
      for (int k = 0; k < array2.length; k++) { 
       //Declare a 1D Array to hold current row from array2 
       double[] p1 = new double[array2[k].length]; 

       //Iterate through Columns of current array2 Row... 
       for (int l = 0; l < array2[k].length; l++) { 
        //Place current array2 row into a 1D Array p1 
        p1[l] = array2[k][l]; 

        //Get the KL Divergence fpr p0 and p1 1D arrays 
        //and display it within the Console window 
        double kld = klDivergence(p0, p1); 

        //Display to Console 
        System.out.println("The Divergence between Row " + i + 
          " of " + nameForArray1 + " and Row " + k + " of " + 
          nameForArray2 + " is: --> " + kld); 
       } 
      } 
     } 
    } 
} 

這將是您輕鬆修改此方法準確滿足您的需求。由於你原來的文章,我假設你的二維數組是相對於特定的期間,因此period0 [] [],period1 [] [],period2 [] [],最後是period3 [] []]。 。因此,在四個2D雙類型數組將結構通常爲:

double[][] period0 = { 
     {0.15250886479593964,0.2610516793197853,0.11441768814194446,0.1265241345428162,0.3454976331995246}, 
     {0.14389124837314887,0.10513281153155449,0.1833462741873425,0.36788054102686596,0.1997491248810186}, 
     {0.1111207312911868,0.17499901413730568,0.2914581757577288,0.20433331657432438,0.2180887622394655}, 
     {0.0948730457966342,0.19288720600625753,0.19471332499886804,0.18018001280247228,0.3373464103957629}, 
     {0.18877271931210932,0.26521449714587747,0.13230019262559328,0.27631809895720494,0.13739449195931552} 
     };  

double[][] period1 = { 
     {0.1274517393962726,0.10526928843184565,0.35751329613481436,0.12240396832200726,0.2873617077151316}, 
     {0.3016290729137225,0.09902028076323677,0.17515717333485062,0.35620664945852193,0.06798682352968743}, 
     {0.0948730457966342,0.19288720600625753,0.19471332499886804,0.18018001280247228,0.3373464103957629}, 
     {0.18877271931210932,0.26521449714587747,0.13230019262559328,0.27631809895720494,0.13739449195931552}, 
     {0.17804585265772793,0.25651982583759037,0.3860867129515085,0.09453797159458521,0.08480963695844175} 
     }; 

double[][] period2 = { 
     {0.2311120677942418,0.07901250493611567,0.15795189397863776,0.24546018732208122,0.28646334596884354}, 
     {0.08823944830766299,0.26313933789756516,0.10406419933285384,0.3365866979847223,0.20797031647719286}, 
     {0.1274517393962726,0.10526928843184565,0.35751329613481436,0.12240396832200726,0.2873617077151316}, 
     {0.3016290729137225,0.09902028076323677,0.17515717333485062,0.35620664945852193,0.06798682352968743}, 
     {0.11962680738039468,0.1590225091909952,0.24009305610431117,0.11189649648370673,0.36936113084052996} 
     }; 

double[][] period3 = { 
     {0.17804585265772793,0.25651982583759037,0.3860867129515085,0.09453797159458521,0.08480963695844175}, 
     {0.08823944830766299,0.26313933789756516,0.10406419933285384,0.3365866979847223,0.20797031647719286}, 
     {0.1274517393962726,0.10526928843184565,0.35751329613481436,0.12240396832200726,0.2873617077151316}, 
     {0.0948730457966342,0.19288720600625753,0.19471332499886804,0.18018001280247228,0.3373464103957629}, 
     {0.3962773409768214,0.12002724792315751,0.15722439889764284,0.11854502459707339,0.20792598760527947} 
     }; 

現在我們需要做的是調用我們的kldFromDoubleArrays()方法來處理你想要的時間。在您的文章中,您指定要處理的行是:

  • period0的每一行對應period1的每一行;
  • period1的每一行對應period2的每一行;
  • period2的每一行對應period3的每一行;

所以,知道這會調用我們的方法三次:

//Create a Underline for Console window display. 
String ul = String.join("", Collections.nCopies(100, "=")) + "\n"; 

//Period0 To Period1 Comparison: 
kldFromDoubleArrays(period0, "Period 0", period1, "Period 1"); 
System.out.println(ul); 

//Period1 To Period2 Comparison: 
kldFromDoubleArrays(period1, "Period 1", period2, "Period 2"); 
System.out.println(ul); 

//Period2 To Period3 Comparison: 
kldFromDoubleArrays(period2, "Period 2", period3, "Period 3"); 
System.out.println(ul); 

下面是一些示例輸出:

The Divergence between Row 2 of Period 0 and Row 1 of Period 1 is: --> -0.16008580289377392 
The Divergence between Row 2 of Period 0 and Row 1 of Period 1 is: --> -0.16008580289377392 
The Divergence between Row 2 of Period 0 and Row 1 of Period 1 is: --> -0.16008580289377392 
The Divergence between Row 2 of Period 0 and Row 1 of Period 1 is: --> -0.16008580289377392 
The Divergence between Row 2 of Period 0 and Row 1 of Period 1 is: --> -0.16008580289377392 
The Divergence between Row 2 of Period 0 and Row 2 of Period 1 is: --> 0.025341952815786797 
The Divergence between Row 2 of Period 0 and Row 2 of Period 1 is: --> 0.025341952815786797 
The Divergence between Row 2 of Period 0 and Row 2 of Period 1 is: --> 0.025341952815786797 
The Divergence between Row 2 of Period 0 and Row 2 of Period 1 is: --> 0.025341952815786797 
The Divergence between Row 2 of Period 0 and Row 2 of Period 1 is: --> 0.025341952815786797 
The Divergence between Row 2 of Period 0 and Row 3 of Period 1 is: --> -0.08495427575998642 
The Divergence between Row 2 of Period 0 and Row 3 of Period 1 is: --> -0.08495427575998642 
The Divergence between Row 2 of Period 0 and Row 3 of Period 1 is: --> -0.08495427575998642 

而且一切差不多了。我希望這有助於你。祝你的項目好運。

+0

謝謝:)我使用那種木槌方法,但我有一個問題,我的週期是動態的,我可能有幾百個週期,所以我不能創建像這樣的期間 – mstfky

+0

這確實很奇怪....因爲我沒有創建它們......你在你的初始文章中做過。這並不重要,因爲只要它們在兩個數組中都包含相同數量的列,就可以將任何您喜歡的2D雙類型數組傳遞給** kldFromDoubleArrays()**方法。它聽起來像你需要的是協助創建從您正在接收的特定雙類型數據的一維或二維數組...我不確定,因爲在這一點上,我仍然困惑於你的真正需求是什麼。爲了進一步幫助您,我需要查看一些真實的數據以及您想要使用的數據。 – DevilsHnd

+0

您想要處理的數據是否以穩定的流形式進入,並且您在收到時需要實時分歧?或者,它是否作爲數據文件進入?我不知道......現在就在這裏猜測。 – DevilsHnd

0

我發現了一個解決方案。

int numOfTopicsInEachPeriod=5; 

double[][] myFirstRow=new double [numOfTopicsInEachPeriod][myDistributions[0].length]; 
double[][] mySecondRow=new double[numOfTopicsInEachPeriod][myDistributions[0].length]; 


int count =0; 
int counter =0; 
int temp=0; 

for(int j =0;j<myDistributions.length-numOfTopicsInEachPeriod;j++){ 

    int mod=j%numOfTopicsInEachPeriod; 
    int countOfTopics = j/numOfTopicsInEachPeriod; 
    count=0; 

    if(mod==0){ 
     temp=1; 
     count=numOfTopicsInEachPeriod* countOfTopics; 

    } 

    if(temp==1&&mod!=0){count=numOfTopicsInEachPeriod* countOfTopics; } 

    for(int i=counter;i<numOfTopicsInEachPeriod;i++){ 

     myFirstRow[i]=myDistributions[count]; 
     mySecondRow[i]=myDistributions[count+5]; 

     System.out.print("myFunction(Row["+j+"],Row ["+(count+5)+"]),"+"\t"); 

     count++; 

    } 

    System.out.println(); 
}