【大模型系列】更像人类行为的爬虫框架

随着大规模模型技术的兴起,我们可以看到百模大战、各种智能体、百花齐放的应用场景,那么作为一名前端开发者,以前端的视角,我们应当如何积极做好技术储备,开拓技术视野,在智能体时代保持一定的竞争力呢?我尝试通过一系列文章来总结一下!

前言

可能很多人会好奇,你写爬虫就写爬虫为啥要和大模型扯上关系,明显的蹭热点吧。其实我们在做大模型应用时,比如问答系统、内容生成等应用时,通常会用到检索增强生成 (RAG) 技术,标准 RAG(以智能问答🌰) 流程图如下,大致分为以下几个步骤:

在这里插入图片描述

离线部分

  1. 知识库:数据从各种来源收集并存储在知识库中。
  2. 清洗、装载:数据进行预处理和清洗,以确保数据质量、清洗后的数据被装载为文档。
  3. 文档:将预处理后的数据组织成文档格式。
  4. 切分:将文档切分成更小的段(chunks),以便后续处理。
  5. 向量化:将切分后的文档段通过向量模型转换为向量表示。
  6. 向量数据库:向量化的文档段存储在向量数据库中,便于快速检索。

在线部分

  1. 用户请求:用户发出查询请求。
  2. Prompt: 用户的请求被处理为一个prompt,准备进行向量化。
  3. 向量化:用户请求的prompt通过向量模型转换为向量表示。
  4. 相似度查询:根据向量化的用户请求在向量数据库中进行相似度查询,检索相关的文档段。
  5. 提取相关知识:检索到的相关文档段作为背景知识注入到提示词模板中。
  6. 提示词模板:将检索到的背景知识与用户请求结合,生成完整的提示词。
  7. LLM(大型语言模型):使用提示词生成最终的回答或内容。
  8. 返回用户:最终的生成内容返回给用户。

我们可以看到,我们的回答是否准确,是否具备差异性,来源于我们的知识库内容的丰富程度和相关性。而知识库内容的获取途径,其中重要的组成部分就是爬虫。

关键概念

如果你以前了解过爬虫相关概念,在讲到爬虫的时候,脑子里蹦出来的会有以下关键词

  1. JS 渲染(JavaScript Rendering)

在现代网页中,很多内容是通过 JavaScript 动态加载和渲染的。这意味着传统的静态网页爬虫(如直接抓取 HTML 内容的爬虫)可能无法获取这些动态加载的内容。因此,爬虫需要具备执行 JavaScript 的能力,以便能够完全渲染页面并获取所有需要的数据。

  1. 无头浏览器(Headless Browsers)

无头浏览器是一种在没有图形用户界面的环境中运行的浏览器。这类浏览器能够执行 JavaScript,并可以模拟用户在浏览器中的操作,如点击、输入文本和滚动页面。常用的无头浏览器有 Puppeteer 和 Playwright,它们基于 Chrome 和 Firefox 等主流浏览器内核,提供了强大的网页自动化和爬取功能。

  1. 等待元素渲染(Waiting for Elements to Render)

由于网页内容可能是动态加载的,爬虫在抓取页面内容时需要等待特定元素加载完成。无头浏览器通常提供了等待元素出现的方法(如 waitForSelector),以确保页面完全加载后再进行数据提取。这样可以避免抓取到不完整的内容或空白页面。

  1. 代理服务器(Proxy Server)

为了防止被目标网站封禁和提高爬取效率,爬虫通常会使用代理服务器。代理服务器可以隐藏爬虫的真实 IP 地址,并通过轮换多个代理 IP 来模拟不同的访问来源,避免爬取行为被检测到并封禁。使用代理服务器还能绕过地理限制,访问特定区域的网站内容。

接下来我给大家介绍一个爬虫框架,并实现一个简单的例子,让大家了解下这个框架。

功能介绍

[Crawlee] 是一个高效的网页爬虫和抓取工具,旨在帮助开发者快速构建可靠的爬虫系统。它兼具HTTP请求和无头浏览器的爬取能力,适用于各种动态和静态网页内容的抓取。包含 node 和 python两个版本

在这里插入图片描述

🌈 主要功能
  • HTTP和无头浏览器爬取:支持传统的HTTP请求和现代无头浏览器(如Playwright和Puppeteer),可以抓取动态生成的内容。
  • 持久化队列:自动管理和持久化URL队列,确保高效和可靠的抓取过程。(广度优先和深度优先)
  • 自动扩展:支持根据需求动态调整爬取规模,提高抓取效率。
  • 代理轮换:内置代理轮换功能,避免IP被封,提高爬取的稳定性。
  • 生命周期管理:提供灵活的生命周期管理,允许自定义爬虫的各个阶段。
  • 错误处理和重试机制:自动处理爬取过程中遇到的错误,并进行重试,确保数据完整性。
👍 优势
  • 单一接口:统一的接口处理HTTP和浏览器爬取,简化开发过程,减少学习成本。
  • JavaScript渲染支持:通过无头浏览器渲染页面,抓取动态内容,使得爬取结果更完整。
  • 丰富的配置选项:提供多种配置选项,适应不同的爬取需求,增强灵活性。http2浏览器请求他fingerprints
  • TypeScript编写:利用TypeScript的强类型检查和自动补全功能,提高代码质量和开发效率。
  • 内置快速HTML解析器,如Cheerio和JSDOM
  • CLI和Docker支持:提供命令行工具和Docker支持,方便集成和部署,适应不同的开发环境。
🆚 与其他爬虫框架对比
  • Scrapy:Scrapy 是一个强大的传统HTTP爬取框架,但不支持动态内容的抓取。Crawlee 在处理动态内容方面更有优势,特别是对现代Web应用的抓取。
  • BeautifulSoup:BeautifulSoup 主要用于解析HTML,功能相对简单,不具备Crawlee 的自动扩展、代理轮换和生命周期管理等高级功能。
  • Selenium:Selenium 可以抓取动态内容,但缺少持久化队列和自动扩展功能,且性能相对较低。Crawlee 提供了更高效和集成的解决方案。

Crawlee 主打一个高效、可高、速度极快,接下来我们通过一个 demo,来了解它有哪些功能!

Live Demo

目标:挑战 20 分钟,完成掘金前端话题内容的爬取,并完成结构化存储

⚠️注意以下示例代码,大部分都是 github 的 copilot 帮我补全的,我只提供思路,他就帮我写完了!!!

初始化项目

打开一个终端,执行以下命令

crawlee 提供 3 个类,方便用户针对不同场景选择不同的类

  • [CheerioCrawler] 主要针对普通 http 的爬取,并通过 cheerio 库来解释 html,快速高效,但无法处理 js 渲染
  • [PuppeteerCrawler] google 开源的无头浏览器[Puppeteer],提供标准 API 来控制 Chrome/Firefox
  • [PlaywrightCrawler] microsoft 开源的无头浏览器**[playwright])** ,提供标准 API 来控制 Chrome/Firefox、Webkit 等浏览器,功能更加齐全

由于笔者原来一直使用 puppeteer,以下会使用 PuppeteerCrawler 来完成 demo,其中 cheerio 可以理解为 node 版本的 jQuery,提供强大 dom 操作

# 你也可以通过以下命令,通过官方模版初始化应用
# npx crawlee create juejin-crawlercd juejin-crawler
npm init
npm install --save crawlee cheerio puppeteer
安装依赖、启动脚本

打开 package.json修改以下内容,关键两个改动

  • 为了简单,我们是用 esm 来解析 js 文件,需增加 "type": "module",
  • 增加一个启动脚本 "start": "rm -rf storage/ && node src/main.mjs", 其中 main 文件在后续创建
{"name": "juejin-crawler","version": "1.0.0","main": "index.js","scripts": {"start": "rm -rf storage/ && node src/main.mjs","test": "echo \"Error: no test specified\" && exit 1"},"type": "module","author": "","license": "ISC","description": "","dependencies": {"cheerio": "^1.0.0-rc.12","crawlee": "^3.11.1","puppeteer": "^22.15.0"}
}
增加入口文件

增加一个入口文件 src/main.mjs

  • 需要引入一个 router 文件,用来处理整体 handler 操作,包括如何处理列表页、如何处理详情页等等
  • 需要引入一个 config 文件,主要用来配置结构化数据所需的配置,比如爬取页面 URL、页面对于的选择器,如 title 对应详情页的 article-title
  • 初始化一个PuppeteerCrawler实例,具体配置作用,见代码
  • 把请求入口链接加到队列,并启动任务

main.mjs 整体内容如下

import { PuppeteerCrawler, ProxyConfiguration, log } from 'crawlee';
import { router } from './routes.mjs';
import config from './config.mjs';log.setLevel(log.LEVELS.DEBUG);log.debug('Setting up crawler.');
// const proxyConfiguration = new ProxyConfiguration({
//   proxyUrls: [],
// });// 创建 PuppeteerCrawler 实例
const crawler = new PuppeteerCrawler({// 是否使用会话池,启用后爬虫会重用会话和 Cookie// useSessionPool: true,// 是否为每个会话持久化 Cookie,启用后每个会话会有自己的 Cookie 存储// persistCookiesPerSession: true,// 代理配置,用于通过代理服务器发送请求,可以用于绕过 IP 限制或地理位置限制// proxyConfiguration,// 最大并发请求数,控制同时进行的请求数量maxConcurrency: 10,// 每分钟最大请求数,控制每分钟发送的请求数量maxRequestsPerMinute: 20,// 启动上下文配置launchContext: {launchOptions: {// 是否以无头模式启动浏览器(无头模式:没有图形界面),设置为 false 表示有图形界面headless: false,},},// 爬虫运行时的最大请求数量,当达到这个数量时,爬虫会停止maxRequestsPerCrawl: 1000,// requestHandler 定义了爬虫在访问每个页面时要做的操作// 可以在这里提取数据、处理数据、保存数据、调用 API 等requestHandler: router,// 处理请求失败的情况,记录失败的请求并输出错误日志failedRequestHandler({ request, log }) {log.error(`Request ${request.url} failed too many times.`);},
});// 添加要爬取的请求,config 是一个包含 URL 和标签的数组
// 这里将每个 item 的 url 和 label 添加到爬虫的请求队列中
await crawler.addRequests(config.map(item => { return { url: item.url, label: item.label } }));// 启动爬虫
await crawler.run();
增加配置文件,增加灵活性

增加一个配置文件 src/config.mjs ,具体实现以下功能

  • 配置要爬取的页面 URL,给定一个标签,如 juejin
  • 配置各个字段的选择器,这个对于前端工程师来说,小菜一碟,截图看看例子

在这里插入图片描述

具体配置信息如下:

export default [{label: 'juejin',url: 'https://juejin.cn/frontend',selector: {detail: '.entry-list .title-row a',title: 'h1.article-title',author: '.author-info-box .author-name a span',modifiedDate: '.author-info-box .meta-box time',hit: '.author-info-box .meta-box .views-count',readTime: '.author-info-box .meta-box .read-time',description: '.article-header p',content: '.article-viewer',},}
]
增加处理逻辑

增加真正处理逻辑文件 src/routes 这里增加两个处理逻辑,列表页和详情页

  • 列表页:通过模拟滚动的方式,触发滚动底部加载更多,并把列表页所有文章加入爬取队列
  • 详情页:通过配置的选择器,把详情页的数据结构化,并存储到数据集
  • 如果这里为了实现知识库相关功能,也可以把拿到的数据存储到向量数据库,这里不做演示
import { createPuppeteerRouter, Dataset } from 'crawlee';// import { Article } from './db.mjs';
export const router = createPuppeteerRouter();import config from './config.mjs';config.map(async item => {const dataset = await Dataset.open(item.label);// 打开列表页操作router.addHandler(`${item.label}`, async ({ request, page, enqueueLinks, log }) => {page.setDefaultTimeout(5000);log.debug(`Enqueueing pagination: ${request.url}`)// 由于掘金是滚动加载,这里通过模拟滚动到底部,实现页面切换const scrollToBottom = async (page, scrollDelay = 5000) => {let previousHeight;let newHeight;let reachedEnd = false;let count = 0;// 这里只滚动2次,如果还没有到底部,可以根据实际情况调整while (!reachedEnd && count < 2) {previousHeight = await page.evaluate('document.body.scrollHeight');await page.evaluate(`window.scrollBy(0, ${previousHeight})`);await new Promise(resolve => setTimeout(resolve, scrollDelay));newHeight = await page.evaluate('document.body.scrollHeight');count++;if (previousHeight === newHeight) {reachedEnd = true;}}};// 模拟滚动加载await scrollToBottom(page);// 等待页面加载完成,这里只为演示,在这个例子中,不需要等待await page.waitForSelector(item.selector.detail);// 把列表页的详情页链接加入到爬虫队列中await enqueueLinks({selector: item.selector.detail,label: `${item.label}-DETAIL`,});await page.close();});// 打开详情页操作router.addHandler(`${item.label}-DETAIL`, async ({ request, page, log }) => {page.setDefaultTimeout(5000);log.debug(`Extracting data: ${request.url}`)const urlParts = request.url.split('/').slice(-2);const url = request.url;await page.waitForSelector(item.selector.content);const details = await page.evaluate((url, urlParts, item) => {return {url,uniqueIdentifier: urlParts.join('/'),type: urlParts[0],title: document.querySelector(item.selector.title).innerText,author: document.querySelector(item.selector.author).innerText,modifiedDate: document.querySelector(item.selector.modifiedDate).innerText,hit: document.querySelector(item.selector.hit).innerText,readTime: document.querySelector(item.selector.readTime).innerText,content: document.querySelector(item.selector.content).innerText,contentHTML: document.querySelector(item.selector.content).innerHTML,};}, url, urlParts, item);log.debug(`Saving data: ${request.url}`)// await Article.create(details);await dataset.pushData(details);await page.close();});});
router.addDefaultHandler(async ({ request, page, enqueueLinks, log }) => {log.error(`Unhandled request: ${request.url}`);
});
启动爬虫
npm start

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

打开 chrome 浏览器,按照逻辑自动打开列表页、详情页

在这里插入图片描述

数据存储到 storage 目录下,并按照我们定义的结构,以 json 格���保存起来

增加代理 IP Server

由于上面的例子我做了限制,如果爬取并发数太高的话,大概率会被封禁,所以这个时候就需要用到代理 ip 服务 和 session 管理

  • Proxy 管理:如果有代理 URL,只需以下几行代码,即可实现代理访问,并通过 proxyInfo 方法检查当前代理
import { PuppeteerCrawler, ProxyConfiguration } from 'crawlee';
const proxyConfiguration = new ProxyConfiguration({proxyUrls: ['http://proxy-1.com', 'http://proxy-2.com'],
});
const crawler = new PuppeteerCrawler({useSessionPool: true,persistCookiesPerSession: true,proxyConfiguration,async requestHandler({ proxyInfo }) {console.log(proxyInfo);},
});
  • session 管理:使用 session 管理,主要为了过滤掉被阻止或者不工作的代理,大致代码如下:
import { PuppeteerCrawler, ProxyConfiguration } from 'crawlee';const proxyConfiguration = new ProxyConfiguration({/* opts */
});const crawler = new PuppeteerCrawler({// To use the proxy IP session rotation logic, you must turn the proxy usage on.proxyConfiguration,// Activates the Session pool (default is true).useSessionPool: true,// Overrides default Session pool configurationsessionPoolOptions: { maxPoolSize: 100 },// Set to true if you want the crawler to save cookies per session,// and set the cookies to page before navigation automatically (default is true).persistCookiesPerSession: true,async requestHandler({ page, session }) {const title = await page.title();if (title === 'Blocked') {session.retire();} else if (title === 'Not sure if blocked, might also be a connection error') {session.markBad();} else {// session.markGood() - this step is done automatically in PuppeteerCrawler.}},
});

以上,大功告成!!


在这里插入图片描述

如何学习AI大模型?

我在一线互联网企业工作十余年里,指导过不少同行后辈。帮助很多人得到了学习和成长。

我意识到有很多经验和知识值得分享给大家,也可以通过我们的能力和经验解答大家在人工智能学习中的很多困惑,所以在工作繁忙的情况下还是坚持各种整理和分享。但苦于知识传播途径有限,很多互联网行业朋友无法获得正确的资料得到学习提升,故此将并将重要的AI大模型资料包括AI大模型入门学习思维导图、精品AI大模型学习书籍手册、视频教程、实战学习等录播视频免费分享出来。

在这里插入图片描述

第一阶段: 从大模型系统设计入手,讲解大模型的主要方法;

第二阶段: 在通过大模型提示词工程从Prompts角度入手更好发挥模型的作用;

第三阶段: 大模型平台应用开发借助阿里云PAI平台构建电商领域虚拟试衣系统;

第四阶段: 大模型知识库应用开发以LangChain框架为例,构建物流行业咨询智能问答系统;

第五阶段: 大模型微调开发借助以大健康、新零售、新媒体领域构建适合当前领域大模型;

第六阶段: 以SD多模态大模型为主,搭建了文生图小程序案例;

第七阶段: 以大模型平台应用与开发为主,通过星火大模型,文心大模型等成熟大模型构建大模型行业应用。

在这里插入图片描述

👉学会后的收获:👈
• 基于大模型全栈工程实现(前端、后端、产品经理、设计、数据分析等),通过这门课可获得不同能力;

• 能够利用大模型解决相关实际项目需求: 大数据时代,越来越多的企业和机构需要处理海量数据,利用大模型技术可以更好地处理这些数据,提高数据分析和决策的准确性。因此,掌握大模型应用开发技能,可以让程序员更好地应对实际项目需求;

• 基于大模型和企业数据AI应用开发,实现大模型理论、掌握GPU算力、硬件、LangChain开发框架和项目实战技能, 学会Fine-tuning垂直训练大模型(数据准备、数据蒸馏、大模型部署)一站式掌握;

• 能够完成时下热门大模型垂直领域模型训练能力,提高程序员的编码能力: 大模型应用开发需要掌握机器学习算法、深度学习框架等技术,这些技术的掌握可以提高程序员的编码能力和分析能力,让程序员更加熟练地编写高质量的代码。

在这里插入图片描述

1.AI大模型学习路线图
2.100套AI大模型商业化落地方案
3.100集大模型视频教程
4.200本大模型PDF书籍
5.LLM面试题合集
6.AI产品经理资源合集

👉获取方式:
😝有需要的小伙伴,可以保存图片到wx扫描二v码免费领取【保证100%免费】🆓

在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/399913.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

ElasticSearch聚合操作详解

文章目录 聚合操作聚合的分类测试数据Metric AggregationBucket Aggregation获取job的分类信息限定聚合范围Range & Histogram聚合聚合嵌套 Pipeline Aggregation聚合的作用范围排序ES聚合分析不精准原因分析聚合性能优化启用 eager global ordinals 提升高基数聚合性能插入…

打造高效信息发布平台小程序:设计思路与实践

在当今这个信息爆炸的时代&#xff0c;信息发布平台已成为连接用户与内容的桥梁&#xff0c;小程序以其独特的优势成为众多企业和个人开发者青睐的选择。开发一款专注于信息发布与共享的小程序&#xff0c;旨在为用户打造一个便捷、高效、互动性强的信息获取平台&#xff0c;具…

luckyexcel 编辑预览excel文件

luckyexcel 编辑预览excel文件 支持后端传文件流预览编辑&#xff0c;也支持选择本地文件编辑预览 看效果 上代码 <template><div style"margin: 30px"><div class"button-box2"><div><div style"color: red">…

Windows File Recovery卡在99%怎么解决?实用指南!

为什么会出现“Windows File Recovery卡在99%”的问题&#xff1f; Windows File Recovery&#xff08;Windows文件恢复&#xff09;是微软设计的命令行应用程序。它可以帮助用户从健康/损坏/格式化的存储设备中恢复已删除/丢失的文件。 通过输入相关命令&#xff0c;设置源/…

整理 酷炫 Flutter 开源UI框架 按钮

flutter_percent_indicator Flutter 百分比指示器库 项目地址&#xff1a;https://github.com/diegoveloper/flutter_percent_indicator 项目Demo&#xff1a;https://download.csdn.net/download/qq_36040764/89631340

jenkins 安装以及自动构建maven项目并且运行

在这里找到你对应jdk的版本的jenkins包 War Jenkins Packages 我这里用的使java8,所以下载 https://mirrors.jenkins.io/war-stable/2.60.1/jenkins.war 然后jenkins可以安装到centos系统 在本地windows系统运行命令行 scp C:\Users\98090\Downloads\jenkins.war root@192…

模拟三层--控制层、业务层和数据访问层

三层的概念:https://developer.aliyun.com/article/1390024 一、新建一个项目 我新建好的项目名为spring__ioc_02,然后在 src-main-java 下建立三层&#xff08;数据访问层、业务层和控制层&#xff09;的包 dao、service 和controller、并在包下建立相应的接口和实现类 Proje…

【2】初识JVM

目录 一.什么是JVM 二.JVM的功能 2.1即时编译 三.常见的JVM​编辑 ​编辑 总结​编辑 一.什么是JVM 二.JVM的功能 2.1即时编译 三.常见的JVM 总结

基于Java中的SSM框架实现高校就业管理系统项目【项目源码+论文说明】计算机毕业设计

基于Java中的SSM框架实现高校就业管理系统演示 摘要 本论文主要讲述了基于SSM框架及MySQL数据库实现的就业管理系统的设计和开发过程。本论文中所讲的就业管理系统是通过所学的知识创办一个非商业性的网站平台&#xff0c;使所有想要就业信息查看的高校毕业生们与想要宣传自己…

Spring Web MVC入门(中)

1. 请求 访问不同的路径, 就是发送不同的请求. 在发送请求时, 可能会带⼀些参数, 所以学习Spring的请求, 主要 是学习如何传递参数到后端以及后端如何接收. 传递参数, 咱们主要是使⽤浏览器和Postman来模拟&#xff1b; 1.1 传递单个参数 接收单个参数&#xff0c;在Spring MV…

Spring boot敏感参数加密配置

一&#xff0c;背景 在项目中很多参数会被配置到配置文件中&#xff0c;比如说密钥&#xff0c;用户名&#xff0c;数据库连接&#xff0c;账号密码之类的&#xff0c;如果用明文配置&#xff0c;会有一定的安全风险。为了减小风险&#xff0c;增加对敏感配置数据的加密配置。…

路径规划 | 五种经典算法优化机器人路径规划(Matlab)

目录 效果一览基本介绍程序设计参考文献 效果一览 基本介绍 五种经典算法优化机器人路径规划&#xff0c;算法可任意更换&#xff01;地图可修改&#xff01;Matlab语言 1.分为简单路径规划和复杂路径规划两种情景&#xff0c;采用粒子群算法(PSO)&#xff0c;遗传算法(GA)&am…

快速上手Spring Boot

快速上手Spring Boot (qq.com)

YOLO基础-目标检测的性能指标详解与计算方法

目标检测是计算机视觉中的重要任务&#xff0c;主要目的是在图像中识别并定位特定的物体。YOLO&#xff08;You Only Look Once&#xff09;系列模型作为目标检测领域的代表性方法之一&#xff0c;凭借其高效和准确的特点&#xff0c;广泛应用于实际场景中。本文通过详细介绍目…

AI技术在招聘数据分析洞察中的作用

一、引言&#xff1a;AI赋能招聘新纪元 在数字化转型浪潮中&#xff0c;人工智能技术&#xff08;AI&#xff09;正以前所未有的速度渗透至各行各业&#xff0c;其中&#xff0c;招聘领域正经历着一场深刻的变革。传统招聘模式依赖于人工筛选简历、面试评估等低效且主观性强的…

2024年翻译工具新风尚:实时翻译与精准度并进

语言交流的障碍随着全球化的不断深入日益成为连接不同文化和国家的挑战。然而&#xff0c;在科技日新月异的今天&#xff0c;类似谷歌翻译这样的工具正在高速发展这。这次我们来一起探讨深受用户喜欢的翻译工具有哪些。 1.福昕在线翻译 链接直达&#xff1a;https://fanyi.pd…

数据结构 - 位图 | 布隆过滤器

文章目录 一、位图1、位图概念2、实现一个简略的位3、位图的优缺点4、位图的应用场景 二、布隆过滤器1、提出2、概念3、布隆过滤器的实现 三、海量数据处理1、哈希切割2、面试题 一、位图 1、位图概念 位图&#xff08;Bitmap&#xff09;是一种非常高效的数据结构&#xff0c…

MySQL基础练习题38-每位教师所教授的科目种类的数量

目录 题目 准备数据 分析数据 总结 题目 查询每位老师在大学里教授的科目种类的数量。 准备数据 ## 创建库 create database db; use db;## 创建表 Create table If Not Exists Teacher (teacher_id int, subject_id int, dept_id int)## 向表中插入数据 Truncate table…

[Megagon Labs] Annotating Columns with Pre-trained Language Models

Annotating Columns with Pre-trained Language Models 任务定义 输入&#xff1a;一张数据表&#xff0c;但没有表头&#xff0c;只有表中的数据。 输出&#xff1a;每一列数据的数据类型&#xff0c;以及两列数据之间的关系。 数据类型和数据关系都是由训练数据决定的固定…

自建Gitlab和Gitlab runner并推送镜像到Harbor

1. 创建虚拟机 整体规划如下 1.1 创建3台虚拟机 系统版本Centos7.9 设置IP分别为 192.168.200.201 、192.168.200.202、 192.168.200.203 1.2 安装docker 3台虚拟机都安装docker&#xff0c;参考文章 安装docker 1.3 修改daemon.json 修改 /etc/docker/daemon.json 文件…