开发使用的mongo,但是现在需要面试,很多公司是使用mysql的,所以复习一下吧
mysql语句
1. left join
当使用表a左连接left join表b,如果表a的一条数据在表b种不能找到,也会输出这一条数据,不存在的数值为null。
选择要输出的列 a left join b on 连接条件
right join也是同样的道理
mongo里也有联表查询,我有使用过
下面是一个例子,但是最好不要使用联表查询,比较慢。
有用户表user,用户宠物表pet。用户分服,用serverId表示。
想获取某个服上一批宠物的信息(本来可以直接在pet种找,但是由于前期的设计问题,没有给pet加上serverId这个属性),就需要使用mongo的联表查询了。mongo的联表查询使用管道(管道类似物理意义上的管道,管道对input数据进行操作,再output处理后的数据。管道可以有多个)。联表操作使用的是lookup关键字。值得注意的地方是as这里,官方的解释是在从表中的匹配到的数据,会作为数组,放在管道中输入数据的后面。由于这个字段是数组,所以后面需要用unwind来拆分。
{
$lookup:
{
from: <collection to join>,
localField: <field from the input documents>,
foreignField: <field from the documents of the "from" collection>,
as: <output array field>
}
}
type Pet struct{
PetId int64 `bson:"petId"`
ServerId int32 `bson:"serverId"`
Level int32 `bson:"level"`
Color int32 `bson:"color"`
Gender int32 `bson:"gender"`
Attr map[int32]int32 `bson:"attr"`
}
filter := bson.M{ //过滤条件:宠物等级小于等于10
"level": bson.M{"$lte": 10},
}
lookUp := bson.M{ //联表语句
"from": "user", //从表
"localField": "userId", //主表字段
"foreignField": "userId", //从表字段
"as": "user", //从表的数据的别名,
//后面使用从表需要使用到
}
c := mgdb.Collection(_const.MONGO_NAME, _const.MINION_TABLE)
pipe := []bson.M{
{
"$match": filter, //匹配主表
},
{
"$lookup": lookUp,
},
{
"$match": bson.D{ //匹配从表
{"user.serverId", _const.SERVICE_ID},
},
},
{ //拆分从表中找到的数组,成为单独的文件
"$unwind": "$user",
},
{ //保留哪些字段
"$project": bson.M{
"petId": 1,
"attr": 1,
"level": 1,
"color": 1,
"gender": 1,
"serverId": "$user.serverId",
},
},
{
"$sample": bson.M{
"size": limit,
},
},
}
cur, err := c.Aggregate(context.TODO(), pipe)
if err != nil {
logrus.Println("聚合错误: ", err)
return nil
}
var res []*Pet
defer cur.Close(context.TODO())
for cur.Next(context.TODO()) {
pet := &Pet{}
if err := cur.Decode(pet); err == nil {
res = append(res, pet)
} else {
logrus.Println("Decode err: ", err)
}
}
2. order by
select
(select distinct e.salary
from
Employee e
order by e.salary desc
limit 1 offset 1)
as SecondHighestSalary
上面这种写法我没能理解为什么用临时表就可以输出null,使用ifnull比较好理解, ifnull(v1, v2), 如果v1为null,则输出v2
select
ifnull(
(select distinct e.salary
from
Employee e
order by e.salary desc
limit 1 offset 1),
null) as SecondHighestSalary
操作 | sql | mongo |
---|---|---|
升序 | asc | sort: {字段:1} |
降序 | desc | sort: {字段:-1} |
限制输出个数 | limit n | limit n |
跳过的个数 | offest n | skip n |
mysql的limit的后面可以跟两个数,表示第一个表示偏移量和第二个表示输出的行数
3. 排序
终于找到工作了,要去上班了