增加了Driver对表中某字段通过主键批量更新的功能.

测试用代码.
    	$m=M('think\model\Adv:log');
    	for($i=0;$i<=10000;$i++)
    	{
    		$m->bulkSave(array('id'=>$i,'admin_id'=>$i*2));
    	}
    	$m->bulkSave(true);
对一万条记录的特定字段做单独更新,耗时0.46秒.如不使用字段绑定或者缩减绑定字符.可能会更小.
This commit is contained in:
zizhilong
2016-02-11 15:49:29 +08:00
parent f883ca5aac
commit 9072e85ff0

View File

@@ -924,6 +924,51 @@ abstract class Driver
return $this->execute($sql, $this->getBindParams(true), !empty($options['fetch_sql']) ? true : false);
}
/**
* 批量更新某字段
* @access public
* @param mixed $field 字段名
* @param mixed $pk 主键名
* @param mixed $dataSet 数据集
* @param mixed $operator 运算符
* @param array $options 参数表达式
**/
public function updateFieldAll($field,$pk,$dataSet,$operator = '=',$options = [])
{
$values = [];
$this->bind = array_merge($this->bind, !empty($options['bind']) ? $options['bind'] : []);
$field = $this->parseKey($field);
$pk = $this->parseKey($pk);
if(in_array($operator,['+','-'])){
$operator = '= ' . $field . $operator;
}
$value = '';
foreach ($dataSet as $key => $val) {
if (is_array($val) && 'exp' == $val[0]) {
$value = $val[1];
} elseif (is_null($val)) {
$value = 'NULL';
} elseif (is_scalar($val)) {
if (0 === strpos($val, ':') && isset($this->bind[substr($val, 1)])) {
$value = $val;
} else {
$name = count($this->bind);
$value = ':' . $_SERVER['REQUEST_TIME'] . '_' . $name;
$this->bindParam( $_SERVER['REQUEST_TIME'] . '_' . $name, $val);
}
}
//没使用过非数字主键,怎么处理比较合适?
$values[] = " WHEN " .$key." THEN " . $value;
}
$sql = 'UPDATE ' . $this->parseTable($options['table']) . ' SET ' . $field . $operator . ' CASE ' . $pk . implode(' ', $values) . ' END ' ;
//查询条件需和WHEN THEN对一致
$sql .= ' WHERE ' . $pk . ' in (' . implode(',',array_map([$this,'parseValue'],array_keys($dataSet))) . ')';
$sql .= $this->parseComment(!empty($options['comment']) ? $options['comment'] : '');
return $this->execute($sql, $this->getBindParams(true), !empty($options['fetch_sql']) ? true : false);
}
/**
* 批量插入记录
* @access public