#python #tensorflow #keras #word2vec #word-embedding
#python #tensorflow #keras #word2vec #word-встраивание
Вопрос:
Я пытаюсь выполнить генерацию текста на уровне word и застрял с последующей проблемой:
Мои входные данные выглядят следующим образом:
tokenized_seq = [[w2v_model.wv.vocab[word].index for word in w2v_data[i]] for i in range(len(w2v_data))]
x_seq = []
y_seq = []
for seq in tokenized_seq:
x_seq.append(seq[:-1])
y_seq.append([seq[-1]])
Итак, я иду вдоль последовательности (кодированные слова, используемые в word2vec) с переходящим окном фиксированного размера (маркированный _seq — это список последовательностей фиксированной длины).
Посмотрите пример:
Блок кода:
print(x_seq[0], '->', y_seq[0])
print(' '.join([w2v_model.wv.index2word[i] for i in x_seq[0]]), '->', w2v_model.wv.index2word[y_seq[0].pop()])
Вывод:
[608, 1661, 1, 4260, 1, 3, 2978, 741, 0, 153, 740, 1, 12004] -> [109]
часть первая . i . — eh bien , mon prince . gênes -> et
Итак, тогда я пытаюсь ввести все вышеперечисленное для встраиваемого слоя.
model = Sequential()
model.add(Embedding(input_dim=vocab_size,
output_dim=emdedding_size,
input_length=avg_sent_len-1,
weights=[predtrained_weights]
trainable=False))
model.add(Bidirectional(LSTM(units=128)))
model.add(Dense(units=vocab_size, activation='softmax'))
model.compile(loss='categorical_crossentropy', optimizer='adam', metrics=['accuracy'])
history = model.fit(x_seq, y_seq,
epochs=10,
batch_size=128,
validation_split=0.2,
verbose=2)
Параметрами встраивания являются:
predtrained_weights = w2v_model.wv.vectors
vocab_size, emdedding_size = w2v_model.wv.vectors.shape
avg_sent_len
является ли длина каждой последовательности в x_seq
Модель компилируется хорошо, но при установке я получаю следующую ошибку:
ValueError: Error when checking target: expected dense_40 to have shape (31412,) but got array with shape (223396,)
(31412,) является vocab_size
223396 — это x_seq
или y_seq
длина (количество входных последовательностей)
Итак, кто-нибудь может мне помочь?
Ответ №1:
Ваши входные данные x_seq
должны быть одним массивом numpy shape (batch_size, seq_len)
. Попробуйте добавить x_seq = np.array(x_seq)
.
Комментарии:
1. Спасибо, это помогло, но у меня все еще есть проблемы с встраиванием входных данных. Ожидается, что входные данные будут иметь форму
vocab_size
, но доказанный ввод (и я думаю, это правильный путь) являетсяx_seq.shape
, что не одно и то же. Итак, я немного запутался2. Вероятно, проблема в слое BiLSTM, следующем за вашим слоем встраивания.
input_shape
Этот слой должен быть(seq_len, embedding_size)
, а не(vocab_size, seq_len)
таким, как вы написали в своем коде. Если это не помогло, пожалуйста, укажите сообщение об ошибке, которое вы получаете.3.Я пытался использовать оба неуказанных LSTM:
model.add(Bidirectional(LSTM(units=128))
l ike в примерах bunch и указать форму ввода, как вы сказали:model.add(Bidirectional(LSTM(units=128, input_shape=(len(x_seq), emdedding_size))))
И оба способа не помогли. Я получаю сообщение об ошибке:ValueError: Error when checking target: expected dense_34 to have shape (31412,) but got array with shape (223396,)
31412, это размер vocab, 223396 — длинаx_seq
(ввода)4. Эта ошибка связана с целевыми объектами (
y_seq
), а не с входными данными (x_seq
). Ваша цель должна иметь форму(batch_size, vocab_size)
, где каждая из строк является одной с горячим кодированием. И вы действительно можете просто исключитьinput_shape
из слоя LSTM.5. Если вы используете
categorical_crossentropy
as loss, ваши метки определенно должны быть в горячем кодировании. В качестве альтернативы вы можете использоватьsparse_categorical_crossentropy
. В этом случае ваши метки должны иметь форму(batch_size, 1)
и не должны быть закодированы горячим способом. Например, следующие фиктивные данные будут работать с разреженной категориальной кроссэнтропией:x_seq = np.random.rand(n_samples, seq_len)
иy_seq = np.random.randint(0, vocab_size, n_samples).reshape((-1,1))
.