向量數學

本節涵蓋向量數學和向量操作函數。

陣列

可以使用 array 函數建立陣列。

例如,以下運算式會建立一個具有三個元素的數值陣列

array(1, 2, 3)

當此運算式傳送到 /stream 處理程式時,它會回應一個 JSON 陣列

{
  "result-set": {
    "docs": [
      {
        "return-value": [
          1,
          2,
          3
        ]
      },
      {
        "EOF": true,
        "RESPONSE_TIME": 0
      }
    ]
  }
}

視覺化

zplot 函數可用於使用 Zeppelin-Solr 來視覺化向量。

我們先看看當我們將陣列函數視覺化為表格時會發生什麼事。

array

它會顯示為一行,其中包含以逗號分隔的值清單。您會發現您無法使用任何繪圖工具來視覺化此輸出。

若要繪製陣列,您需要 zplot 函數。我們先看看 zplot 輸出在 JSON 格式中的樣子。

zplot(x=array(1, 2, 3))

當此運算式傳送到 /stream 處理程式時,它會回應一個 JSON 陣列

{
  "result-set": {
    "docs": [
      {
        "x": 1
      },
      {
        "x": 2
      },
      {
        "x": 3
      },
      {
        "EOF": true,
        "RESPONSE_TIME": 0
      }
    ]
  }
}

zplot 已將陣列轉換為具有欄位 x 的三個元組。

讓我們新增另一個陣列

zplot(x=array(1, 2, 3), y=array(10, 20, 30))

當此運算式傳送到 /stream 處理程式時,它會回應一個 JSON 陣列

{
  "result-set": {
    "docs": [
      {
        "x": 1,
        "y": 10
      },
      {
        "x": 2,
        "y": 20
      },
      {
        "x": 3,
        "y": 30
      },
      {
        "EOF": true,
        "RESPONSE_TIME": 0
      }
    ]
  }
}

現在我們有三個元組,其中包含 xy 欄位。

讓我們看看 Zeppelin-Solr 如何以表格格式處理此輸出

xy

現在我們定義了 xy 欄,我們可以簡單地切換到其中一個折線圖,並使用圖表設定來插入要繪製的欄位

line1

每個圖表都有設定,可以透過點擊設定來探索。

您可以為不同類型的視覺化在圖表類型之間切換。以下是長條圖的範例

bar

陣列操作

陣列可以作為參數傳遞給對陣列進行操作的函數。

例如,可以使用 rev 函數反轉陣列

rev(array(1, 2, 3))

當此運算式傳送到 /stream 處理程式時,它會回應

{
  "result-set": {
    "docs": [
      {
        "return-value": [
          3,
          2,
          1
        ]
      },
      {
        "EOF": true,
        "RESPONSE_TIME": 0
      }
    ]
  }
}

另一個範例是 length 函數,它會傳回陣列的長度

length(array(1, 2, 3))

當此運算式傳送到 /stream 處理程式時,它會回應

{
  "result-set": {
    "docs": [
      {
        "return-value": 3
      },
      {
        "EOF": true,
        "RESPONSE_TIME": 0
      }
    ]
  }
}

可以使用 copyOfRange 函數取得陣列的切片,該函數會從起始和結束範圍複製陣列的元素。

copyOfRange(array(1,2,3,4,5,6), 1, 4)

當此運算式傳送到 /stream 處理程式時,它會回應

{
  "result-set": {
    "docs": [
      {
        "return-value": [
          2,
          3,
          4
        ]
      },
      {
        "EOF": true,
        "RESPONSE_TIME": 0
      }
    ]
  }
}

可以使用 ltrim(左修剪)和 rtrim(右修剪)函數修剪陣列的元素。 ltrimrtrim 函數會從陣列的左側或右側移除特定數量的元素。

以下範例顯示 lrtim 函數修剪陣列的前 2 個元素

ltrim(array(0,1,2,3,4,5,6), 2)

當此運算式傳送到 /stream 處理程式時,它會回應

{
  "result-set": {
    "docs": [
      {
        "return-value": [
          2,
          3,
          4,
          5,
          6,
        ]
      },
      {
        "EOF": true,
        "RESPONSE_TIME": 1
      }
    ]
  }
}

依索引取得值

可以使用 valueAt 函數依索引擷取向量中的值。

valueAt(array(0,1,2,3,4,5,6), 2)

當此運算式傳送到 /stream 處理程式時,它會回應

{
  "result-set": {
    "docs": [
      {
        "return-value": 2
      },
      {
        "EOF": true,
        "RESPONSE_TIME": 0
      }
    ]
  }
}

序列

sequence 函數可用於以陣列形式產生數字序列。以下範例會傳回 10 個數字的序列,從 0 開始,步幅為 2。

sequence(10, 0, 2)

當此運算式傳送到 /stream 處理程式時,它會回應

{
  "result-set": {
    "docs": [
      {
        "return-value": [
          0,
          2,
          4,
          6,
          8,
          10,
          12,
          14,
          16,
          18
        ]
      },
      {
        "EOF": true,
        "RESPONSE_TIME": 7
      }
    ]
  }
}

natural 函數可用於建立從零開始的自然數序列。自然數是正整數。

以下範例會建立一個從零開始的序列,其中包含所有直到但不包括 10 的自然數。

natural(10)

當此運算式傳送到 /stream 處理程式時,它會回應

{
  "result-set": {
    "docs": [
      {
        "return-value": [
          0,
          1,
          2,
          3,
          4,
          5,
          6,
          7,
          8,
          9
        ]
      },
      {
        "EOF": true,
        "RESPONSE_TIME": 0
      }
    ]
  }
}

向量排序

可以使用 asc 函數依自然遞增順序對陣列進行排序。

以下範例顯示 asc 函數排序陣列

asc(array(10,1,2,3,4,5,6))

當此運算式傳送到 /stream 處理程式時,它會回應

{
  "result-set": {
    "docs": [
      {
        "return-value": [
          1,
          2,
          3,
          4,
          5,
          6,
          10
        ]
      },
      {
        "EOF": true,
        "RESPONSE_TIME": 1
      }
    ]
  }
}

向量摘要與範數

有一組函數可以執行摘要並返回陣列的範數。這些函數會對陣列進行運算並返回單一值。以下是可用的向量摘要與範數函數:multaddsumSqmeanl1norml2normlinfnorm

以下範例顯示 mult 函數,該函數會將陣列中的所有值相乘。

mult(array(2,4,8))

當此運算式傳送到 /stream 處理程式時,它會回應

{
  "result-set": {
    "docs": [
      {
        "return-value": 64
      },
      {
        "EOF": true,
        "RESPONSE_TIME": 0
      }
    ]
  }
}

向量範數函數提供不同的公式來計算向量的大小。

以下範例計算陣列的 l2norm

l2norm(array(2,4,8))

當此運算式傳送到 /stream 處理程式時,它會回應

{
  "result-set": {
    "docs": [
      {
        "return-value": 9.16515138991168
      },
      {
        "EOF": true,
        "RESPONSE_TIME": 0
      }
    ]
  }
}

純量向量運算

純量向量運算函數會將純量值與向量中的每個值進行加、減、乘或除。以下函數執行這些運算:scalarAddscalarSubtractscalarMultiplyscalarDivide

以下是 scalarMultiply 函數的範例,它會將純量值 3 與陣列中的每個值相乘。

scalarMultiply(3, array(1,2,3))

當此運算式傳送到 /stream 處理程式時,它會回應

{
  "result-set": {
    "docs": [
      {
        "return-value": [
          3,
          6,
          9
        ]
      },
      {
        "EOF": true,
        "RESPONSE_TIME": 0
      }
    ]
  }
}

逐元素向量運算

可以使用逐元素向量運算函數來對兩個向量進行加、減、乘和除。可用的逐元素向量運算函數有:ebeAddebeSubtractebeMultiplyebeDivide

以下表達式執行兩個陣列的逐元素相減。

ebeSubtract(array(10, 15, 20), array(1,2,3))

當此運算式傳送到 /stream 處理程式時,它會回應

{
  "result-set": {
    "docs": [
      {
        "return-value": [
          9,
          13,
          17
        ]
      },
      {
        "EOF": true,
        "RESPONSE_TIME": 5
      }
    ]
  }
}

點積與餘弦相似度

dotProductcosineSimilarity 函數通常用作兩個稀疏向量之間的相似度量。dotProduct 是角度和大小的量度,而 cosineSimilarity 僅是角度的量度。

以下是 dotProduct 函數的範例

dotProduct(array(2,3,0,0,0,1), array(2,0,1,0,0,3))

當此運算式傳送到 /stream 處理程式時,它會回應

{
  "result-set": {
    "docs": [
      {
        "return-value": 7
      },
      {
        "EOF": true,
        "RESPONSE_TIME": 15
      }
    ]
  }
}

以下是 cosineSimilarity 函數的範例

cosineSimilarity(array(2,3,0,0,0,1), array(2,0,1,0,0,3))

當此運算式傳送到 /stream 處理程式時,它會回應

{
  "result-set": {
    "docs": [
      {
        "return-value": 0.5
      },
      {
        "EOF": true,
        "RESPONSE_TIME": 7
      }
    ]
  }
}