HTML5中的数据存储sessionStorage、localStorage

news2024/9/20 22:05:30

第8章 HTML5中的数据存储

之前通常使用Cookie存储机制将数据保存在用户的客户端。

H5增加了两种全新的数据存储方式:Web Stroage和Web SQL Database.

前者用于临时或永久保存客户端少量数据,后者是客户端本地化的一套数据库系统。

8.1 Web Storage存储简介

Web Storage API分为会话数据和长期数据,相应的API分为两类:

sessionStorage(保存会话数据)

localStorage(在客户端长期保存数据)

整体优于Cookie方式。

8.1.1 sessionStorage对象

保存数据短暂,打开浏览器时可以查看操作过程中临时保存的数据,一旦关闭浏览器,所有sessionStorage对象保存的数据将全部丢失。一下是调用方法:

  • sessionStorage.setItem(key,value):key表示保存内容的键名,value是键值,名不能重复。
  • sessionStorage.getItem(key):返回指定键名对应的键值,若不存在则返回null。
1.功能描述

页面中,创建一个文本框与读取按钮,用户在文本框中输入内容时,通过sessionStorage对象保存文本框输入的内容,及时显示在页面中,单击读取按钮时,将直接读取被保存的临时数据。

2.实现代码
<!DOCTYPE html>
<html>
    <head>
        <meta charset="utf-8">
        <title>使用sessionStorage对象保存与读取临时数据</title>
        <script>
            function txtNameChange(v) {
                var strName = v.value;
                //保存数据
                sessionStorage.setItem("strName",strName);
                var pStatus = document.getElementById("pStatus");
                pStatus.style.display="block";
                pStatus.innerHTML=sessionStorage.getItem("strName");
            }
            function btnGetValue(){
                var pStatus = document.getElementById("pStatus");
                pStatus.style.display="block";
                pStatus.innerHTML=sessionStorage.getItem("strName");
            }
        </script>
    </head>
    <body>
        <fieldset>
            <legend>sessionStorage对象保存与读取临时数据</legend>
            <input type="text" name="txtName" class="inputTxt" 
             size="30px" onchange="txtNameChange(this);" />
            <input type="button" name="btnGetValue" class="inputbtn"
             onclick="btnGetValue();" value="读取"/>
             <p id="pStatus"></p>
        </fieldset>
    </body>
</html>
3.页面效果

刷新后,还可以读到,但是关闭浏览器,进来,无法读到。

8.1.2 localStorage对象

sessionStorage只能保存临时会话数据,关闭浏览器后,数据清空。

如果需要长期在客户端保存数据,建议用localStorage对象,直至人工清除为止。

对应的方法:

  • localStorage.setItem(key,value):同sessionStorage.
  • localStorage.getItem(key):同sessionStorage.
  • localStorage.removeItem(key):key表示要删除的键名,一旦删除,与键名相应的数据全部被删除。
1.功能描述

新建登录页面,用户在文本框中输入用户名与密码,单击登录按钮后,将使用localStorage对象保存登录时的用户名,如果选中是否保存密码,则保存密码,否则清空原先保存的密码,重新打开浏览器,将保存的用户名和密码数据分别显示在文本框中。

2.代码实现
<!DOCTYPE html>
<html>

<head>
    <meta charset="utf-8">
    <title>使用localStorage对象保存与读取登录用户名与密码</title>
    <style>
        * {
            list-style-type: none;
        }

        .status {
            background-color: dodgerblue;
            border: 1px solid;
            color: white;
        }
    </style>
    <script>
        function $$(id) {
            return document.getElementById(id);
        }
        //页面加载时调用的函数
        function pageload() {
            var strName = localStorage.getItem("keyName");
            var strPass = localStorage.getItem("keyPass");
            if (strName) {
                $$("txtName").value = strName;
            }
            if (strPass) {
                $$("txtPass").value = strPass;
            }
        }
        //单击登录按钮后调用的函数
        function btnLogin() {
            var strName = $$("txtName").value;
            var strPass = $$("txtPass").value;
            localStorage.setItem("keyName", strName);
            if ($$("chkSave").checked) {
                localStorage.setItem("keyPass", strPass);
            } else {
                localStorage.removeItem("keyPass");
            }
            $$("spnStatus").className = "status";
            $$("spnStatus").innerHTML = "登录成功!";
        }
    </script>
</head>

<body onload="pageload();">
    <form action="#" id="frmLogin">
        <fieldset>
            <legend><!-- 字段说明 -->
                登录
            </legend>
            <ul>
                <li class="li_top">
                    <span id="spnStatus"></span>
                </li>
                <li>名称:<input type="text" id="txtName" class="inputTxt" /></li>
                <li>密码:<input type="password" id="txtPass" class="inputTxt" /></li>
                <li><input type="checkbox" id="chkSave" />是否保存密码</li>
                <li class="li_bot">
                    <input type="button" class="inputbtn" value="登录" onclick="btnLogin();" />
                    <input type="reset" class="inputbtn" value="取消" />
                </li>
            </ul>
        </fieldset>
    </form>
</body>

</html>
3.页面效果

注意:尽管localStorage对象可以将数据长期保存在客户端,但是跨浏览器读取数据时,被保存的数据不可共用。

8.2 localStorage详解

8.2.1 清空localStorage数据

上面学的removeItem()只能单挑删除,想要清空所有保存的数据用clear().

1.功能描述

新建页面中添加两个按钮,使用localStorage对象保存6条顺序记录,另一个用于清空记录。

2.实现代码
<!DOCTYPE html>
<html>

<head>
    <meta charset="utf-8">
    <title>清空localStorage对象保存的全部数据</title>
    <script>
        function $$(id) {
            return document.getElementById(id);
        }
        var intNum = 0;
        //单击增加按钮时调用
        function btnAdd() {
            for (var i = 0; i < 6; i++) {
                localStorage.setItem("strKeyName" + i, "strKeyValue" + i);
                intNum++;
            }
            $$("pStatus").innerHTML = "已成功保存<b>" + intNum + "</b>条数据记录!";
        }
        //单击清空按钮
        function btnDel() {
            localStorage.clear();
            $$("pStatus").innerHTML = "已成功清空全部数据记录!";
        }

    </script>
</head>

<body>
    <input id="btnAdd" type="button" value="增加" class="inputbtn" onclick="btnAdd();" />
    <input id="btnDel" type="button" value="清空" class="inputbtn" onclick="btnDel();" />
    <p id="pStatus"></p>
</body>

</html>
3.页面效果

8.2.2 遍历localStorage数据

为了查看所有保存的数据信息,通常要遍历这些数据,遍历过程中,需要访问另外两个属性:

length与key,前者是总数,后者是键名项,常与索引号index配合。

1.功能描述

创建页面,通过遍历获取对象保存的全部点评数据记录,在文本框中输入点评内容,单击发表后,可以通过localStorage对象保存输入的数据,并实时显示到页面中。

2.实现代码
<!DOCTYPE html>
<html>

<head>
    <meta charset="utf-8">
    <title>遍历localStorage数据</title>
    <style>
        span {
            display: inline-block;
            width: 100px;
            margin: 0 10px;
        }
    </style>
    <script>
        function $$(id) {
            return document.getElementById(id);
        }

        //指定长度的随机数
        function retRandomNum(n) {
            var strRnd = "";
            for (var i = 0; i < n; i++) {
                strRnd += Math.floor(Math.random() * 10);
            }
            return strRnd;
        }

        //单击发表按钮调用
        function btnAdd() {
            //获取文本框的内容
            var strContent = $$("txtContent").value;
            //定义一个日期型对象
            var strTime = new Date();
            //如果不为空,则保存
            if (strContent.length > 0) {
                var strKey = "cnt" + retRandomNum(4);
                var strVal = strContent + "," + strTime.toLocaleTimeString();
                localStorage.setItem(strKey, strVal);
            }
            //重新加载
            getLocalData();
            //清空原先内容
            $$("txtContent").value = "";
        }

        //获取保存数据并显示在页面中
        function getLocalData() {
            //标题部分
            var strHTML = "<li><span>编号</span><span>内容</span><span>时间</span></li>";
            //内容部分
            var strArr = new Array();
            for (var i = 0; i < localStorage.length; i++) {
                //获取key值
                var strKey = localStorage.key(i);
                //过滤键名内容
                if (strKey.substring(0, 3) == "cnt") {
                    var strVal = localStorage.getItem(strKey);
                    strArr = strVal.split(",");
                    strHTML += "<li><span>" + strKey + "</span>";
                    strHTML += "<span>" + strArr[0] + "</span>";
                    strHTML += "<span>" + strArr[1] + "</span></li>";
                }
            }
            $$("ulMessage").innerHTML = strHTML;
        }

    </script>
</head>

<body onload="getLocalData();">
    <ul id="ulMessage">正在读取数据...</ul>
    <p class="p4">
        <textarea id="txtContent" class="txtContent" cols="30" rows="10"></textarea><br />
        <input id="btnAdd" type="button" value="发表" onclick="btnAdd();" />
    </p>
</body>

</html>
3.页面效果

4.源码分析

随机数4位的取法关注一下,通过索引取key值小技巧用一下。

8.2.3 使用JSON对象存取数据

H5中可以通过localStorage数据与JSON对象互转,快速实现存储更多数据的功能。

转JSON对象方法:

  • JSON.parse(data),data表示对象获取的数据,返回装载data数据的JSON对象。
  • JSON.stringify(obj),将对象转为JSON格式的文本数据。
1.功能描述

创建一个简单的学生信息管理页面,用户输入姓名,分数,选择性别,单击增加按钮后,使用JSON中的stringify()方法,将数据保存在localStorage对象中,同时,调用JSON中的parse()方法实时显示新增学生数据信息。

2.实现代码
<!DOCTYPE html>
<html>

<head>
    <meta charset="utf-8">
    <title>使用JSON对象存储数据</title>
    <style>
        ul span {
            display: inline-block;
            width: 100px;
            margin: 0 10px;
        }
    </style>
    <script>
        function $$(id) {
            return document.getElementById(id);
        }
        function btnAdd() {
            var strStuID = $$("txtStuID").value;
            var strName = $$("txtName").value;
            var strSex = $$("selSex").value;
            var strScore = $$("txtScore").value;
            if (strName.length > 0 && strScore.length > 0) {
                //定义1个实体对象,保存全部获取的值
                var SetData = new Object();
                SetData.StuID = strStuID;
                SetData.Name = strName;
                SetData.Sex = strSex;
                SetData.Score = strScore;
                var strTxtData = JSON.stringify(SetData);
                localStorage.setItem(strStuID, strTxtData);
            }
            //重新加载
            getLocalData();
            //清空原先内容
            $$("txtName").value = "";
            $$("txtScore").value = "";
        }
        //获取保存数据并显示到页面上
        function getLocalData() {
            //标题部分
            var strHTML = "<li><span>学号</span><span>姓名</span>" +
                "<span>性别</span><span>总分</span></li>";
            //内容部分
            for (var i = 0; i < localStorage.length; i++) {
                //获取key值
                var strKey = localStorage.key(i);
                //过滤键名内容
                if (strKey.substring(0, 3) == "stu") {
                    var GetData = JSON.parse(localStorage.getItem(strKey));
                    strHTML += "<li><span>" + GetData.StuID + "</span>";
                    strHTML += "<span>" + GetData.Name + "</span>";
                    strHTML += "<span>" + GetData.Sex + "</span>";
                    strHTML += "<span>" + GetData.Score + "</span></li>";
                }
            }
            $$("ulMessage").innerHTML = strHTML;
            $$("txtStuID").value = "stu" + retRandomNum(4);
        }
        //指定长度的随机数
        function retRandomNum(n) {
            var strRnd = "";
            for (var i = 0; i < n; i++) {
                strRnd += Math.floor(Math.random() * 10);
            }
            return strRnd;
        }
    </script>
</head>

<body onload="getLocalData();">
    <ul id="ulMessage">正在读取数据...</ul>
    <p>
        <span>学号:<input type="text" id="txtStuID" readonly size="10" /></span><br />
        <span>姓名:<input type="text" id="txtName" size="10" /></span>
        <span>性别:
            <select id="selSex">
                <option value="男">男</option>
                <option value="女">女</option>
            </select>
        </span>
        <br />
        <span>总分:<input type="text" id="txtScore" size="10" /></span>
    <p>
        <input type="button" id="btnAdd" value="增加" onclick="btnAdd();" />
    </p>
    </p>
</body>

</html>
3.页面效果

4.源码分析

可以不借助后台数据来进行增删改查了。

8.2.4 管理localStorage数据

通过JSON对对象进行存取,还可以通过键名,查询、更新、删除对应的键值记录,真正实现对localStorage对象保存数据的管理功能。

1.功能描述

在8.1.3的基础上,添加输入查询内容的文本框与查询按钮,同时,在列表内容项中新增编辑和删除链接。单击查询按钮时,可以根据输入的学号,返回对应的记录,单击编辑与删除链接时,分别实现根据键名更新或者删除对应的键值数据。

2.实现代码
<!DOCTYPE html>
<html>

<head>
    <meta charset="utf-8">
    <title>管理localStorage数据</title>
    <style>
        ul span {
            display: inline-block;
            width: 100px;
            margin: 0 10px;
        }
    </style>
    <script>
        function $$(id) {
            return document.getElementById(id);
        }
        function btnAdd() {
            var strStuID = $$("txtStuID").value;
            var strName = $$("txtName").value;
            var strSex = $$("selSex").value;
            var strScore = $$("txtScore").value;
            if (strName.length > 0 && strScore.length > 0) {
                //定义1个实体对象,保存全部获取的值
                var SetData = new Object();
                SetData.StuID = strStuID;
                SetData.Name = strName;
                SetData.Sex = strSex;
                SetData.Score = strScore;
                var strTxtData = JSON.stringify(SetData);
                localStorage.setItem(strStuID, strTxtData);
            }
            //重新加载
            getLocalData(0);
            //清空原先内容
            $$("txtName").value = "";
            $$("txtScore").value = "";
        }
        //点击查询按钮调用
        function btnSearch() {
            //获取查询学号
            var strSearch = $$("txtSearch").value;
            //根据学号键名获取数据
            getLocalData(strSearch);
        }
        //获取保存数据并显示到页面上
        function getLocalData(s) {
            //标题部分
            var strHTML = "<li>请输入学号:<input type='text' id='txtSearch' size='22' />";
            strHTML += "<input id='btnSearch' type='button' value='查询' onClick='btnSearch();' /></li>";
            strHTML += "<li><span>学号</span><span>姓名</span>" +
                "<span>性别</span><span>总分</span><span>操作</span></li>";
            //内容部分
            if (s) {
                var SearchData = JSON.parse(localStorage.getItem(s));
                strHTML += "<li><span>" + SearchData.StuID + "</span>";
                strHTML += "<span>" + SearchData.Name + "</span>";
                strHTML += "<span>" + SearchData.Sex + "</span>";
                strHTML += "<span>" + SearchData.Score + "</span>";
                strHTML += "<span><a href='#' onclick=EditData('" + SearchData.StuID + "')>编辑</a> &nbsp;|&nbsp;";
                strHTML += "<a href='#' onclick=DeleteData('" + SearchData.StuID + "')>删除</a></span></li>";
            } else {
                for (var i = 0; i < localStorage.length; i++) {
                    //获取key值
                    var strKey = localStorage.key(i);
                    //过滤键名内容
                    if (strKey.substring(0, 3) == "stu") {
                        var GetData = JSON.parse(localStorage.getItem(strKey));
                        strHTML += "<li><span>" + GetData.StuID + "</span>";
                        strHTML += "<span>" + GetData.Name + "</span>";
                        strHTML += "<span>" + GetData.Sex + "</span>";
                        strHTML += "<span>" + GetData.Score + "</span>";
                        strHTML += "<span><a href='#' onclick=EditData('";
                        strHTML += GetData.StuID;
                        strHTML += "');>编辑</a>&nbsp;|&nbsp;";
                        strHTML += "<a href='#' onclick=DeleteData('";
                        strHTML += GetData.StuID;
                        strHTML += "');>删除</a></span></li>";
                    }
                }
            }

            $$("ulMessage").innerHTML = strHTML;
            $$("txtStuID").value = "stu" + retRandomNum(4);
        }
        //编辑链接
        function EditData(k) {
            //根据键值获取对应的数据
            var EditData = JSON.parse(localStorage.getItem(k));
            $$("txtStuID").value = EditData.StuID;
            $$("txtName").value = EditData.Name;
            $$("selSex").value = EditData.Sex;
            $$("txtScore").value = EditData.Score;
        }
        //删除链接
        function DeleteData(k) {
            localStorage.removeItem(k);
            //重新加载
            getLocalData(0);
        }
        //指定长度的随机数
        function retRandomNum(n) {
            var strRnd = "";
            for (var i = 0; i < n; i++) {
                strRnd += Math.floor(Math.random() * 10);
            }
            return strRnd;
        }
    </script>
</head>

<body onload="getLocalData(0);">
    <ul id="ulMessage">正在读取数据...</ul>
    <p>
        <span>学号:<input type="text" id="txtStuID" readonly size="10" /><br />
            <span>姓名:<input type="text" id="txtName" size="10" /></span>
            <span>性别:
                <select id="selSex">
                    <option value="男">男</option>
                    <option value="女">女</option>
                </select>
            </span>
            <br />
            <span>总分:<input type="text" id="txtScore" size="10" /></span>
            <p>
                <input type="button" id="btnAdd" value="增加" onclick="btnAdd();" />
                <input type="button" id="clear" value="清除全部" onclick="localStorage.clear();" />
            </p>
    </p>
</body>

</html>
3.页面效果

8.3 Web SQL数据库基础(不推荐使用,推荐IndexedDB)

Web Storage只有5MB,键值存储带来诸多不便,除此之外还有WebSQL数据库,WebDB,内置了SQLite数据库,对数据库操作可以通过调用executeSql()方法实现,允许JS控制数据库的操作。

WebDB可以实现数据的本地存储,它提供了关系数据库的基本功能,可以存储页面交互的复杂数据,也能缓存从服务器获取的数据。通过事务驱动,实现对数据的管理,也支持多浏览器的并发操作。

核心方法

以下是规范中定义的三个核心方法:

  1. openDatabase:这个方法使用现有的数据库或者新建的数据库创建一个数据库对象。
  2. transaction:这个方法让我们能够控制一个事务,以及基于这种情况执行提交或者回滚。
  3. executeSql:这个方法用于执行实际的 SQL 查询。

打开数据库

我们可以使用 openDatabase() 方法来打开已存在的数据库,如果数据库不存在,则会创建一个新的数据库,使用代码如下:

var db = openDatabase('mydb', '1.0', 'Test DB', 2 * 1024 * 1024);

openDatabase() 方法对应的五个参数说明:

  1. 数据库名称
  2. 版本号
  3. 描述文本
  4. 数据库大小
  5. 创建回调

第五个参数,创建回调会在创建数据库后被调用。

执行查询操作

执行操作使用 database.transaction() 函数:

var db = openDatabase('mydb', '1.0', 'Test DB', 2 * 1024 * 1024); db.transaction(function (tx) { tx.executeSql('CREATE TABLE IF NOT EXISTS LOGS (id unique, log)'); });

插入数据

在执行上面的创建表语句后,我们可以插入一些数据:

var db = openDatabase('mydb', '1.0', 'Test DB', 2 * 1024 * 1024); db.transaction(function (tx) { tx.executeSql('CREATE TABLE IF NOT EXISTS LOGS (id unique, log)'); tx.executeSql('INSERT INTO LOGS (id, log) VALUES (1, "菜鸟教程")'); tx.executeSql('INSERT INTO LOGS (id, log) VALUES (2, "www.runoob.com")'); });

我们也可以使用动态值来插入数据:

var db = openDatabase('mydb', '1.0', 'Test DB', 2 * 1024 * 1024); db.transaction(function (tx) { tx.executeSql('CREATE TABLE IF NOT EXISTS LOGS (id unique, log)'); tx.executeSql('INSERT INTO LOGS (id,log) VALUES (?, ?)', [e_id, e_log]); });

实例中的 e_id 和 e_log 是外部变量,executeSql 会映射数组参数中的每个条目给 "?"。

读取数据

以下实例演示了如何读取数据库中已经存在的数据:

var db = openDatabase('mydb', '1.0', 'Test DB', 2 * 1024 * 1024);
 
db.transaction(function (tx) {
   tx.executeSql('CREATE TABLE IF NOT EXISTS LOGS (id unique, log)');
   tx.executeSql('INSERT INTO LOGS (id, log) VALUES (1, "菜鸟教程")');
   tx.executeSql('INSERT INTO LOGS (id, log) VALUES (2, "www.runoob.com")');
});
 
db.transaction(function (tx) {
   tx.executeSql('SELECT * FROM LOGS', [], function (tx, results) {
      var len = results.rows.length, i;
      msg = "<p>查询记录条数: " + len + "</p>";
      document.querySelector('#status').innerHTML +=  msg;
    
      for (i = 0; i < len; i++){
         alert(results.rows.item(i).log );
      }
    
   }, null);
});

完整实例

var db = openDatabase('mydb', '1.0', 'Test DB', 2 * 1024 * 1024);
var msg;
 
db.transaction(function (tx) {
    tx.executeSql('CREATE TABLE IF NOT EXISTS LOGS (id unique, log)');
    tx.executeSql('INSERT INTO LOGS (id, log) VALUES (1, "菜鸟教程")');
    tx.executeSql('INSERT INTO LOGS (id, log) VALUES (2, "www.runoob.com")');
    msg = '<p>数据表已创建,且插入了两条数据。</p>';
    document.querySelector('#status').innerHTML =  msg;
});
 
db.transaction(function (tx) {
tx.executeSql('SELECT * FROM LOGS', [], function (tx, results) {
    var len = results.rows.length, i;
    msg = "<p>查询记录条数: " + len + "</p>";
    document.querySelector('#status').innerHTML +=  msg;
 
    for (i = 0; i < len; i++){
        msg = "<p><b>" + results.rows.item(i).log + "</b></p>";
        document.querySelector('#status').innerHTML +=  msg;
    }
}, null);
});

删除记录

删除记录使用的格式如下:

db.transaction(function (tx) { tx.executeSql('DELETE FROM LOGS WHERE id=1'); });

删除指定的数据id也可以是动态的:

db.transaction(function(tx) { tx.executeSql('DELETE FROM LOGS WHERE id=?', [id]);});

更新记录

更新记录使用的格式如下:

db.transaction(function (tx) { tx.executeSql('UPDATE LOGS SET log=\'www.w3cschool.cc\' WHERE id=2'); });

更新指定的数据id也可以是动态的:

db.transaction(function(tx) { tx.executeSql('UPDATE LOGS SET log=\'www.w3cschool.cc\' WHERE id=?', [id]); });


完整实例

var db = openDatabase('mydb', '1.0', 'Test DB', 2 * 1024 * 1024);
var msg;
 
 db.transaction(function (tx) {
    tx.executeSql('CREATE TABLE IF NOT EXISTS LOGS (id unique, log)');
    tx.executeSql('INSERT INTO LOGS (id, log) VALUES (1, "菜鸟教程")');
    tx.executeSql('INSERT INTO LOGS (id, log) VALUES (2, "www.runoob.com")');
    msg = '<p>数据表已创建,且插入了两条数据。</p>';
    document.querySelector('#status').innerHTML =  msg;
 });
 
 db.transaction(function (tx) {
      tx.executeSql('DELETE FROM LOGS  WHERE id=1');
      msg = '<p>删除 id 为 1 的记录。</p>';
      document.querySelector('#status').innerHTML =  msg;
 });
 
 db.transaction(function (tx) {
     tx.executeSql('UPDATE LOGS SET log=\'www.w3cschool.cc\' WHERE id=2');
      msg = '<p>更新 id 为 2 的记录。</p>';
      document.querySelector('#status').innerHTML =  msg;
 });
 
 db.transaction(function (tx) {
    tx.executeSql('SELECT * FROM LOGS', [], function (tx, results) {
       var len = results.rows.length, i;
       msg = "<p>查询记录条数: " + len + "</p>";
       document.querySelector('#status').innerHTML +=  msg;
       
       for (i = 0; i < len; i++){
          msg = "<p><b>" + results.rows.item(i).log + "</b></p>";
          document.querySelector('#status').innerHTML +=  msg;
       }
    }, null);
 });

8.4 IndexedDB详解,库Dexie(持续更新)

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

日本“大米荒”持续!政府再次拒绝投放储备米

KlipC报道&#xff1a;日本多地从7月开始出现“大米荒”&#xff0c;有部分新米上市&#xff0c;但是许多超市的大米仍然存在断购或限购的情况&#xff0c;并且部分新米价格上涨至去年同期的两倍。大阪府官员再次呼吁日本中央政府尽快投放储备米以缓解供应紧张&#xff0c;但遭…

Dynamics CRM Ribbon Workbench-the solution contains non-entity components

今天在一个低版本的环境里准备用Ribbon Workbench去编辑一个按钮时&#xff0c;遇到了如下错误 一开始没当回事&#xff0c;以为是我的解决方案问题&#xff0c;去检查了下&#xff0c;只有一个组件&#xff0c;并且哪怕我把组件换成了某个实体也不行&#xff0c;尝试了其他任何…

开源NAS系统-OpenMediaVault(OMV)共享存储网盘搭建和使用(保姆级教程)

1、OpenMediaVault简介 OpenMediaVault,简称:OMV,是由原 FreeNAS 核心开发成员 Volker Theile 发起的基于 Debian Linux 的开源 NAS 操作系统,主要面向家庭用户和小型办公环境。 OpenMediaVault是一款基于Debian Linux的开源网络附加存储(NAS)操作系统,它提供了强大的存…

酒店智能轻触开关:智慧化的创新实践

在追求高品质住宿体验的今天&#xff0c;酒店智能轻触开关作为智慧酒店建设的关键一环&#xff0c;正逐步成为提升酒店服务品质、优化运营效率、增强顾客满意度的有力工具。本文将深入探讨酒店智能轻触开关如何助力酒店实现智慧化管理&#xff0c;以及它所带来的多重变革。 一、…

大模型时代下,nlp初学者需要怎么入门?

前言 自从 ChatGPT 横空出世以来&#xff0c;自然语言处理&#xff08;Natural Language Processing&#xff0c;NLP&#xff09;研究领域就出现了一种消极的声音&#xff0c;认为大模型技术导致 NLP “死了”。 有人认为 NLP 的市场肯定有&#xff0c;但 NLP 的研究会遇到麻…

图片产生3D模型

HyperHuman 上传图片&#xff0c;点击生成 可以多生成几次&#xff0c;点击应用 让效果再好一点 生成完成之后可以导出为fbx格式

实战|等保2.0 Oracle数据库测评过程

以下等保测评过程以Oracle 11g为例&#xff0c;通过PL/SQL进行管理&#xff0c;未进行任何配置、按照等保2.0标准&#xff0c;2021报告模板&#xff0c;三级系统要求进行测评。 一、身份鉴别 a) 应对登录的用户进行身份标识和鉴别&#xff0c;身份标识具有唯一性&#xff0c;…

E212: Can‘t open file for writing

如图 1. 查看当前用户的用户名和所属组 如果你只想查看当前登录用户的用户名和所属组&#xff0c;可以使用以下命令&#xff1a; whoami groups 检查文件和目录权限&#xff1a; ls -ld /private/var/log/wyhy ls -l /private/var/log/wyhy/market.log 修改文件权限&#…

RAKsmart美国大带宽服务器租用体验怎么样?

RAKsmart是一家提供全球服务器租用服务的知名供应商&#xff0c;其在美国的服务器产品种类多样&#xff0c;包括大带宽服务器、多IP站群服务器以及高防御服务器等&#xff0c;以适应不同业务的需求。rak小编为您整理发布。 下面是对RAKsmart美国大带宽服务器租用的具体介绍&…

计算机毕业设计 大学志愿填报系统 Java+SpringBoot+Vue 前后端分离 文档报告 代码讲解 安装调试

&#x1f34a;作者&#xff1a;计算机编程-吉哥 &#x1f34a;简介&#xff1a;专业从事JavaWeb程序开发&#xff0c;微信小程序开发&#xff0c;定制化项目、 源码、代码讲解、文档撰写、ppt制作。做自己喜欢的事&#xff0c;生活就是快乐的。 &#x1f34a;心愿&#xff1a;点…

随机分类,保持均衡水平Python

1、目的&#xff1a; 10000个样本有4个指标&#xff0c;按照逾期金额分10类&#xff0c;确保每类别逾期金额均衡。 2、数据&#xff1a; 3、思路&#xff1a; 将10000个样本按照逾期金额排序&#xff0c; 等距分箱为2500个类别 增加一列随机数 根据类别和随机数升序排列 增加…

MCU6.用keil新建项目

1.新建项目 打开keil4 2.选择单片机的类型 STC并没有出现在其中,但兼容8051芯片,选Atmel的AT89C51或AT89C52均可 本文选AT89C52 弹出的窗口点否 3.查看项目 4.新建文件 5.保存文件 6.将文件添加到工程 双击Source Group 1 点击Add 7.添加已有的工程 如果要添加已有的工程 8…

Java并发编程实战 09 | 为什么需要

什么是守护线程&#xff1f; 守护线程&#xff08;Daemon Thread&#xff09;是Java中的一种特殊线程&#xff0c;那么相对于普通线程它有什么特别之处呢&#xff1f; 在了解守护线程之前&#xff0c;我们先来思考一个问题&#xff1a;JVM在什么情况下会正常退出&#xff1f;…

腾讯公众号种类这么多,为什么小程序能脱颖而出

在微信公众平台中&#xff0c;公众号和小程序是两种不同的功能实体&#xff0c;它们各自承担着不同的角色和使命。然而&#xff0c;随着小程序的崛起&#xff0c;它在众多功能中逐渐脱颖而出&#xff0c;成为商家和开发者的新宠。具体分析如下&#xff1a; 技术优势与用户体验 …

深入探索协同过滤:从原理到推荐模块案例

文章目录 前言一、协同过滤1. 基于用户的协同过滤&#xff08;UserCF&#xff09;2. 基于物品的协同过滤&#xff08;ItemCF&#xff09;3. 相似度计算方法 二、相似度计算方法1. 欧氏距离2. 皮尔逊相关系数3. 杰卡德相似系数4. 余弦相似度 三、推荐模块案例1.基于文章的协同过…

顶点照明渲染路径

1. 顶点照明渲染路径处理光照的方式 基本思想就是所有的光都按照逐顶点的方式进行计算的&#xff0c;在内置渲染管线中&#xff0c;它只会最多记录8个光源的数据&#xff0c;只会将光相关的数据填充到那些逐顶点相关的内置光源变量 顶点照明渲染路径仅仅是前向渲染路径的一个…

Mybatis-PlusDruid数据源

一、Mybatis-Plus简介 &#xff08;一&#xff09;什么是Mybatis-Plus Mybatis-Plus是一个Mybatis&#xff08;OPENS NEW WINDOW&#xff09;的增强工具&#xff0c;在Mybatis的基础上只做增强不做改变&#xff0c;为简化开发。 &#xff08;二&#xff09;Mybatis-Plus的优…

C语言之头文件,预处理命令#include

0 为什么要添加头文件&#xff1f;为什么要使用头文件&#xff1f; 可以看下下面图片左边&#xff0c;是不使用头文件&#xff0c;假设我们为了实现某些功能&#xff0c;编写的函数&#xff0c;全部声明在主函数之前&#xff0c;写几个函数还行&#xff0c;如果是大型项目&…

Hadoop压缩技术与Hive文件格式详解

目录 文件格式和压缩 Hadoop压缩概述 压缩格式 Hive文件格式 Text File ORC 1&#xff09;文件格式 2&#xff09;结构 3&#xff09;建表语句 Parquet 1&#xff09;文件格式 2&#xff09;结构 3&#xff09;建表语句 压缩 Hive表数据进行压缩 1&#xff09;TextFil…

对话 IDC:一文带你了解低代码的技术趋势和平台选型

近日&#xff0c;葡萄城的活字格企业级低代码开发平台入选《中国低代码开发平台技术评估&#xff0c;2024》技术代表厂商&#xff0c;并在可视化开发、集成能力、开放性和兼容性以及生态能力维度获得五星评价。这一荣誉见证了葡萄城在低代码领域的技术实力与创新成果。 为进一…