linux bash,驼峰式字符串用破折号分隔
- 2024-11-14 08:30:00
- admin 原创
- 17
问题描述:
有没有办法转换这样的内容:
MyDirectoryFileLine
到
my-directory-file-line
我找到了一些将所有字母转换为大写或小写的方法,但不是那样的;有什么想法吗?
解决方案 1:
您可以使用s/([A-Z])/-L/g
查找大写字母并将其替换为破折号和小写字母。但是,这会在行首出现破折号,因此您需要另一个 sed 表达式来处理它。
这应该有效:
sed --expression 's/([A-Z])/-L/g' \n --expression 's/^-//' \n <<< "MyDirectoryFileLine"
解决方案 2:
我建议使用 sed 来做到这一点:
NEW=$(echo MyDirectoryFileLine \n | sed 's/(.)([A-Z])/-/g' \n | tr '[:upper:]' '[:lower:]')
UPD我忘记转换为小写,更新了代码
解决方案 3:
echo MyDirectoryFileLine | perl -ne 'print lc(join("-", split(/(?=[A-Z])/)))'
印刷my-directory-file-line
解决方案 4:
@bilalq 的答案略有不同,涵盖了更多可能的边缘情况:
echo "MyDirectoryMVPFileLine" \n| sed 's/([^A-Z])([A-Z0-9])/-/g' \n| sed 's/([A-Z0-9])([A-Z0-9])([^A-Z])/-/g' \n| tr '[:upper:]' '[:lower:]'
输出依然是:
my-directory-mvp-file-line
但是也:
WhatADeal -> what-a-deal
TheMVP -> the-mvp
DoSomeABTesting -> do-some-ab-testing
The3rdThing -> the-3rd-thing
The3Things -> the-3-things
ThingNumber3 -> thing-number-3
解决方案 5:
这里发布的所有解决方案都不适合我。大多数都不能很好地支持多个平台。@4ndrew 的解决方案很接近,但它在多个大写字符相邻的极端情况下失败了(例如:FooMVPClient
变成foo-mv-pclient
而不是foo-mvp-client
)。
这对我有用:
echo "MyDirectoryMVPFileLine" \n| sed 's/([a-z])([A-Z])/-/g' \n| sed 's/([A-Z]{2,})([A-Z])/-/g' \n| tr '[:upper:]' '[:lower:]'
输出:
my-directory-mvp-file-line
解决方案 6:
我的小小贡献适用于“/”(可能用于目录名称或 github repo 名称)。它并不像它应该的那样干净,但可以完成工作。我以 @Peter 的贡献为基础,然后做了一些调整。
function kebab_case() {
echo -n "$1" |\n sed 's/([^A-Z+])([A-Z0-9])/-/g' |\n sed 's/([0-9])([A-Z])/-/g' |\n sed 's/([A-Z])([0-9])/-/g' |\n sed 's/--/-/g' |\n sed 's/([/])-//g' |\n tr '[:upper:]' '[:lower:]'
}
function assert_kebab_equal() {
local Actual
local Expected
Expected="$1"
Actual="$(kebab_case "$2")"
if [ "${Expected}" != "${Actual}" ]; then
echo Error:
echo " Actual: ${Actual}"
echo "Expected: ${Expected}"
else
echo "$2" "$1" | awk '{ printf "%-30s -> %-40s
", $1, $2}'
fi
}
assert_kebab_equal "abc-def" "AbcDef"
assert_kebab_equal "/abc-def-ghi/def" "/AbcDef-Ghi/Def"
assert_kebab_equal "/ab-cd-ef" "/AbCdEf"
assert_kebab_equal "repo-owner/repo-name" "RepoOwner/RepoName"
assert_kebab_equal "repo-12-owner/repo-12-name" "Repo12Owner/Repo12Name"
assert_kebab_equal "repo-12-3-owner/repo-12-name" "Repo12-3Owner/Repo12Name"
assert_kebab_equal "repo-owner/repo-name" "REPO-OWNER/REPO-NAME"
assert_kebab_equal "repo-owner-2/repo-name" "REPO-OWNER2/REPO-NAME"
assert_kebab_equal "repo-1-owner" "REPO1-OWNER"
assert_kebab_equal "repo-1-owner-1/22-repo-2-name" "REPO1-OWNER1/22REPO-2NAME"
# Outputs:
AbcDef -> abc-def
/AbcDef-Ghi/Def -> /abc-def-ghi/def
/AbCdEf -> /ab-cd-ef
RepoOwner/RepoName -> repo-owner/repo-name
Repo12Owner/Repo12Name -> repo-12-owner/repo-12-name
Repo12-3Owner/Repo12Name -> repo-12-3-owner/repo-12-name
REPO-OWNER/REPO-NAME -> repo-owner/repo-name
REPO-OWNER2/REPO-NAME -> repo-owner-2/repo-name
REPO1-OWNER -> repo-1-owner
REPO1-OWNER1/22REPO-2NAME -> repo-1-owner-1/22-repo-2-name
解决方案 7:
这可能对你有用:
<<<"MyDirectoryFileLine" sed 's/[A-Z]/-l&/g;s/.//'
my-directory-file-line
解决方案 8:
使用GNU sed:
echo "MyDirectoryFileLine"|sed -e 's/([A-Z])/-L/g'
如果这让您感到困扰,那么您只需要去掉第一个破折号:
echo "MyDirectoryFileLine"|sed -e 's/([A-Z])/-L/g' -e 's/^-//'
使用BSD sed 的话会稍微长一些:
echo "MyDirectoryFileLine"|sed -e 's/([A-Z])/-/g' -e 'y/ABCDEFGHIJKLMNOPQRSTUVWXYZ/abcdefghijklmnopqrstuvwxyz/' -e 's/^-//'
更新:BSD 版本将与 GNU 版本兼容,因此我建议使用后者。
解决方案 9:
echo "SomeACRONYMInCamelCaseString" \n | sed -e 's/([a-z])([A-Z])/-L/' \n | sed -e 's/(.*)/L/')
sed -e 's/([a-z])([A-Z])/-L/'
将大写字母替换为连字符,仅当大写字母前面有小写字母时才替换小写字母。sed -e 's/(.*)/L/'
将整个字符串变为小写
相关推荐
热门文章
项目管理软件有哪些?
- 2024年20款好用的项目管理软件推荐,项目管理提效的20个工具和技巧
- 2024年开源项目管理软件有哪些?推荐5款好用的项目管理工具
- 项目管理软件有哪些?推荐7款超好用的项目管理工具
- 项目管理软件哪个最好用?盘点推荐5款好用的项目管理工具
- 项目管理软件有哪些最好用?推荐6款好用的项目管理工具
- 项目管理软件有哪些,盘点推荐国内外超好用的7款项目管理工具
- 2024项目管理软件排行榜(10类常用的项目管理工具全推荐)
- 项目管理软件排行榜:2024年项目经理必备5款开源项目管理软件汇总
- 2024年常用的项目管理软件有哪些?推荐这10款国内外好用的项目管理工具
- 项目管理必备:盘点2024年13款好用的项目管理软件
热门标签
云禅道AD