galoisfield.go 1.3 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465
  1. package utils
  2. // GaloisField encapsulates galois field arithmetics
  3. type GaloisField struct {
  4. Size int
  5. Base int
  6. ALogTbl []int
  7. LogTbl []int
  8. }
  9. // NewGaloisField creates a new galois field
  10. func NewGaloisField(pp, fieldSize, b int) *GaloisField {
  11. result := new(GaloisField)
  12. result.Size = fieldSize
  13. result.Base = b
  14. result.ALogTbl = make([]int, fieldSize)
  15. result.LogTbl = make([]int, fieldSize)
  16. x := 1
  17. for i := 0; i < fieldSize; i++ {
  18. result.ALogTbl[i] = x
  19. x = x * 2
  20. if x >= fieldSize {
  21. x = (x ^ pp) & (fieldSize - 1)
  22. }
  23. }
  24. for i := 0; i < fieldSize; i++ {
  25. result.LogTbl[result.ALogTbl[i]] = int(i)
  26. }
  27. return result
  28. }
  29. func (gf *GaloisField) Zero() *GFPoly {
  30. return NewGFPoly(gf, []int{0})
  31. }
  32. // AddOrSub add or substract two numbers
  33. func (gf *GaloisField) AddOrSub(a, b int) int {
  34. return a ^ b
  35. }
  36. // Multiply multiplys two numbers
  37. func (gf *GaloisField) Multiply(a, b int) int {
  38. if a == 0 || b == 0 {
  39. return 0
  40. }
  41. return gf.ALogTbl[(gf.LogTbl[a]+gf.LogTbl[b])%(gf.Size-1)]
  42. }
  43. // Divide divides two numbers
  44. func (gf *GaloisField) Divide(a, b int) int {
  45. if b == 0 {
  46. panic("divide by zero")
  47. } else if a == 0 {
  48. return 0
  49. }
  50. return gf.ALogTbl[(gf.LogTbl[a]-gf.LogTbl[b])%(gf.Size-1)]
  51. }
  52. func (gf *GaloisField) Invers(num int) int {
  53. return gf.ALogTbl[(gf.Size-1)-gf.LogTbl[num]]
  54. }