求js驼峰式命名(带数字)转化为下划线命名的方法

题目描述

由于mysql数据表命名的关系,导致本人在开发项目时需要将驼峰式命名转化为下划线命名,类似于userName1转为user_name_1,经过我写的函数,部分属性可以转化,部分属性会出问题,求教大神指正!

题目来源及自己的思路

我使用正则表达式查询大写和数字,并在查询到那个字符前面添加“_”

相关代码

// 请把代码文本粘贴到下方(请勿用图片代替代码)

<!DOCTYPE html>
<html lang="en">

<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <meta http-equiv="X-UA-Compatible" content="ie=edge">
  <title>Document</title>
</head>

<body>


  <script>
    var info = {
      id: 1,
      id1: 2,
      userName1: '刘玄德',
      userName2: '刘玄德',
      userName3: '大哥',
      userAge: 45,
      userAge1: 46,
      userAge2: 47
    }

    var info2 = {
      id: 1,
      id_1: 2,
      user_name_1: '刘玄德',
      user_name_2: '刘玄德',
      user_name_3: '刘玄德',
      user_age: 45,
      user_age_1: 46,
      user_age_2: 47
    }

    var changeObj = function (obj) {
      var regNum = new RegExp(/\d/)
      var regStr = new RegExp(/[A-Z]/g)
      var arr = Object.keys(obj);
      arr.forEach((k, index) => {
        console.log('=====打印k=========')
        // console.log(k)
        // debugger
        
        if (!regNum.test(k) && !regStr.test(k)) {//既无数字,也无大写
          console.log("既无数字,也无大写")
          console.log(k)
        }else if( regStr.test(k) ){//有大写
          console.log("检测到大写字母")
          var newK3 = k.replace(/([A-Z])/g, "_$1").toLowerCase();
          console.log(newK3)

          if(regNum.test(newK3)){
            console.log("检测到数字")
            newK4 = newK3.replace(/([0-9])/, "_$1");
            console.log(newK4)
          }

        }else{//有数字
          console.log("检测到数字")
          var newK = k.replace(/([0-9])/, "_$1");
          console.log(newK)
        }
        
      })

    }
    changeObj(info)
  </script>
</body>

</html>

你期待的结果是什么?实际看到的错误信息又是什么?

我希望将info转化为info2的形式

var info = {
      id: 1,
      id1: 2,
      userName1: '刘玄德',
      userName2: '刘玄德',
      userName3: '大哥',
      userAge: 45,
      userAge1: 46,
      userAge2: 47
    }

    var info2 = {
      id: 1,
      id_1: 2,
      user_name_1: '刘玄德',
      user_name_2: '刘玄德',
      user_name_3: '刘玄德',
      user_age: 45,
      user_age_1: 46,
      user_age_2: 47
    }

问题描述

但是我在控制台看到的在userName_2就检测不到大写,打印信息如下:

驼峰.html:39 =====打印k=========
驼峰.html:44 既无数字,也无大写
驼峰.html:45 id
驼峰.html:39 =====打印k=========
驼峰.html:58 检测到数字
驼峰.html:60 id_1
驼峰.html:39 =====打印k=========
驼峰.html:47 检测到大写字母
驼峰.html:49 user_name1
驼峰.html:52 检测到数字
驼峰.html:54 user_name_1
驼峰.html:39 =====打印k=========
驼峰.html:58 检测到数字
驼峰.html:60 userName_2
驼峰.html:39 =====打印k=========
驼峰.html:47 检测到大写字母
驼峰.html:49 user_name3
驼峰.html:52 检测到数字
驼峰.html:54 user_name_3
驼峰.html:39 =====打印k=========
驼峰.html:44 既无数字,也无大写
驼峰.html:45 userAge
驼峰.html:39 =====打印k=========
驼峰.html:47 检测到大写字母
驼峰.html:49 user_age1
驼峰.html:52 检测到数字
驼峰.html:54 user_age_1
驼峰.html:39 =====打印k=========
驼峰.html:58 检测到数字
驼峰.html:60 userAge_2

求教大神可不可以改正下我的代码,指出哪里出了问题?并且怎么改正呢?

阅读 5.8k
2 个回答

可以直接同时匹配大写跟数字 /([A-Z]|\d+)/g
试了下可以实现你的需求

const toLine = hump => hump.replace(/([A-Z]|\d+)/g, (a, l) => `_${l.toLowerCase()}`);

var info = {
  id: 1,
  id1: 2,
  userName1: '刘玄德',
  userName2: '刘玄德',
  userName3: '大哥',
  userAge: 45,
  userAge1: 46,
  userAge2: 47
};

for (let k in info) {
  console.log(toLine(k))
}
<script>
    var info = {
      id: 1,
      id1: 2,
      userName1: '刘玄德',
      userName2: '刘玄德',
      userName3: '大哥',
      userAge: 45,
      userAge1: 46,
      userAge2: 47
    }

    var info2 = {
      id: 1,
      id_1: 2,
      user_name_1: '刘玄德',
      user_name_2: '刘玄德',
      user_name_3: '刘玄德',
      user_age: 45,
      user_age_1: 46,
      user_age_2: 47
    }

    function copy(obj){//用于复制一个对象
      var newobj = {};
      for ( var attr in obj) {
          newobj[attr] = obj[attr];
      }
      return newobj;
    }
    var changeObj = function (obj) {
      var copyobj = copy(obj)
      var regNum = new RegExp(/\d/)
      var regStr = new RegExp(/[A-Z]/g)
      var arr = Object.keys(obj);

      var newObj = {}
      arr.forEach((k, index) => {
        var kArr = k.split('')
        var newK = ''
        kArr.forEach((item,index)=>{
          if(regNum.test(item)){
            kArr[index] = "_" + item
          }
          if(regStr.test(item)){
            kArr[index] = "_" + item.toLowerCase()
          }
        })
        newKey = kArr.join('')
        newObj[newKey] = obj[k]
        console.log(newKey)
        
      })
      console.log(newObj)
      return newObj
    }
    changeObj(info)
  </script>

图片描述

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题