Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/php/240.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Php 如何更正我的函数-Laravel-5.5?_Php_Laravel_Laravel 5.5 - Fatal编程技术网

Php 如何更正我的函数-Laravel-5.5?

Php 如何更正我的函数-Laravel-5.5?,php,laravel,laravel-5.5,Php,Laravel,Laravel 5.5,我编写此函数用于插入数组中的单词: public function ins($array) { foreach ($array as $key => $value) { DB::table('words')->updateOrInsert(['word' => $value]); } } 我使用以下查询为mysql中的重复值创建了索引: CREATE UNIQUE INDEX `idx_word` ON `db`.`words` (word)

我编写此函数用于插入数组中的单词:

public function ins($array)
{
    foreach ($array as $key => $value) {
        DB::table('words')->updateOrInsert(['word' => $value]);
    }

}
我使用以下查询为mysql中的重复值创建了索引:

CREATE UNIQUE INDEX `idx_word` ON `db`.`words` (word);
但当我使用我的函数添加单词时,会出现以下错误:

"SQLSTATE[42000]: Syntax error or access violation: 1064 You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'where (`word` = ?) limit 1' at line 1 (SQL: update `words` set  where (`word` = microsoft) limit 1) ◀"

如何正确使用我在Laravel 5.5中为数据库添加不重复单词的功能?

以下是签名方法:

如果行属性已经存在(在您的例子中,如果单词已经存在),它将根据传递到第二个参数的内容进行更新

要解决问题,只需重复attributes参数以填充values参数:

DB::transaction(function () use ($value) {
    DB::table('words')->updateOrInsert(['word' => $value], ['word' => $value]);
});

您可以这样做:

public function ins($array)
{
    $wordsNotExists = array();
    $wordsToInsert = array();

    $array = array_unique($array);
    $wordsThatExists = DB::table('words')
            ->whereIn('word', $array)
            ->pluck('word');

     $wordsNotExists = array_diff ($array, $wordsThatExists->toArray());

    foreach ($wordsNotExists as $key => $value) {
        $wordsToInsert[] = ['word' => $value];
    }

    DB::table('words')->insert($wordsToInsert);
}

创建索引后,可以使用Raw方法插入数据:

foreach (array_unique($array) as $key => $value) {
    DB::insert('INSERT INTO words VALUES (?) ON DUPLICATE KEY word = VALUES(word)', $value);
}

我认为您应该使用模型而不是查询生成器,例如DB::table

Word.php

<?php

namespace App;

use Illuminate\Database\Eloquent\Model;

class Word extends Model
{
    protected $table = "words";
}

注:未测试,给你一个提纲

签名不是需要
DB::table('words')->updateOrInsert(['word'],[$value])吗?不,它希望两侧都有一个关联数组。代码的速度是多少?谁的代码在你的代码上运行得更快?你的还是Maraboc密码@Chris ForrenceWell,当然,对于超过一百万的大量单词,无论您希望进行什么样的前/后处理;第一步是让它工作,然后重构以提高性能(如果性能有问题)。如果在
foreach
循环期间添加了一个单词会发生什么情况?我想Alex是在询问,在foreach循环进行时,该单词是否在单独的线程/调用中插入数据库;对吗?如果我的单词数组很大怎么办?例如,一百万字。此功能的时间优化程度如何?使用查询示例
INSERT-INTO-word VALUES(?)在重复的关键字上=VALUES(word)@Maraboc抱歉@Maraboc,你没有回答这个问题。假设您有一个200个单词的列表要添加,您需要向数据库请求200个
wherex
,这需要一些时间。在您发出第一个请求时,数据库中不存在第一个单词,您将其放入数组中。但是想象一下,在您检查列表中最后一个200字之前,另一个脚本插入了这个字。我的问题是关于您的脚本在这种情况下的行为。@AlexBlex我同意您的看法,我编辑了本例的答案,添加了
array\u unique()
;)我唯一的建议是,您不需要
protected$table=“words”行,因为默认情况下,它将表名定义为word@ChrisForrence谢谢你的建议。我通常不使用受保护的$table,但为了安全起见,我更愿意将其包含在答案中。:)再次感谢您的建议。这很公平,而且包含它也不会有任何坏处:)
<?php

namespace App;

use Illuminate\Database\Eloquent\Model;

class Word extends Model
{
    protected $table = "words";
}
Word::updateOrCreate(['word' => $value]);