Подтвердить что ты не робот

Как проверить пустую структуру?

Я определяю структуру...

type Session struct {
    playerId string
    beehive string
    timestamp time.Time
}

Иногда я назначаю ему пустой сеанс (потому что nil не представляется возможным)

session = Session{};

Затем я хочу проверить, если он пуст:

if session == Session{} {
     // do stuff...
}

Очевидно, что это не работает. Как его написать?

4b9b3361

Ответ 1

Вы можете использовать == для сравнения с композитным литералом с нулевым значением, потому что все поля сопоставимы:

if (Session{}) == session  {
    fmt.Println("is zero value")
}

пример игровой площадки

Из-за двумерной неопределенности в скобках в скобках требуются круглые скобки.

Альтернативой сравнению всего значения является сравнение поля, которое должно быть установлено на ненулевое значение в действительном сеансе. Например, если идентификатор игрока должен быть!= "" В действительном сеансе, используйте

if session.playerId == "" {
    fmt.Println("is zero value")
}

Ответ 2

Вот еще 3 предложения или методы:

С дополнительным полем

Вы можете добавить дополнительное поле, чтобы указать, была ли эта структура заполнена или пуста. Я намеренно назвал его ready, а не empty, потому что нулевое значение a bool равно false, поэтому, если вы создадите новую структуру типа Session{}, поле ready будет автоматически false, и это скажу вам правду: структура еще не готова (она пуста).

type Session struct {
    ready bool

    playerId string
    beehive string
    timestamp time.Time
}

Когда вы инициализируете структуру, вы должны установить ready в true. Ваш метод isEmpty() больше не нужен (хотя вы можете его создать, если хотите), потому что вы можете просто проверить само поле ready.

var s Session

if !s.ready {
    // do stuff (populate s)
}

Значение этого дополнительного поля bool увеличивается по мере увеличения структуры или наличия полей, которые не сопоставимы (например, slice, map и значения функций).

Использование нулевого значения существующего поля

Это похоже на предыдущее предложение, но оно использует нулевое значение существующего поля, которое считается недействительным, когда структура не пуста. Удобство использования зависит от реализации.

Например, если в вашем примере ваш playerId не может быть пустым string "", вы можете использовать его, чтобы проверить, пустует ли ваша структура следующим образом:

var s Session

if s.playerId == "" {
    // do stuff (populate s, give proper value to playerId)
}

В этом случае стоит включить эту проверку в метод isEmpty(), потому что эта проверка зависит от реализации:

func (s Session) isEmpty() bool {
    return s.playerId == ""
}

И используя его:

if s.isEmpty() {
    // do stuff (populate s, give proper value to playerId)
}

Использовать указатель на вашу структуру

Второе предложение - использовать указатель на вашу структуру: *Session. Указатели могут иметь значения nil, поэтому вы можете проверить их:

var s *Session

if s == nil {
    s = new(Session)
    // do stuff (populate s)
}

Ответ 3

Используя reflect.deepEqual, также работает, особенно когда у вас есть карта внутри структуры

package main

import "fmt"
import "time"
import "reflect"

type Session struct {
    playerId string
    beehive string
    timestamp time.Time
}

func (s Session) IsEmpty() bool {
  return reflect.DeepEqual(s,Session{})
}

func main() {
  x := Session{}
  if x.IsEmpty() {
    fmt.Print("is empty")
  } 
}

Ответ 4

Имейте в виду, что с указателями на структуру вам придется разыменовывать переменную, а не сравнивать ее с указателем на пустую структуру:

session := &Session{}
if (Session{}) == *session {
    fmt.Println("session is empty")
}

Проверьте игровая площадка.

Также здесь вы можете видеть, что структура, содержащая свойство, которое представляет собой срез указателей, не может сравниваться таким же образом...

Ответ 5

В качестве альтернативы другим ответам можно сделать это с синтаксисом, аналогичным тому, как вы изначально планировали, если вы делаете это с помощью инструкции case, а не if:

session := Session{}
switch {
case Session{} == session:
    fmt.Println("zero")
default:
    fmt.Println("not zero")
}

пример игровой площадки

Ответ 6

Возможно, что-то вроде this

package main

import "fmt"
import "time"

type Session struct {
    playerId string
    beehive string
    timestamp time.Time
}

func (s Session) Equal(o Session) bool {
   if(s.playerId != o.playerId) { return false }
   if(s.beehive != o.beehive) { return false }
   if(s.timestamp != o.timestamp) { return false }
   return true
}

func (s Session) IsEmpty() bool {
    return s.Equal(Session{})
}

func main() {
    x := Session{}
    if x.IsEmpty() {
       fmt.Print("is empty")
    } 
}