2017-04-20 16 views
3

我使用许多不同的正则表达式实现,因为这发生在几个系统上(Linux,Windows,VS,记事本++等);这正是我有一个客户想要删除自动调整大小的地方。意图是使用正则表达式,其中有史以来的工具来找到任何有宽度,但没有自动宽度的行,然后加上 autowidth。我只是问如何找到它,,但我打算然后使用我在这里找到的替代字符串中的给定编辑器。我有替换位:我只是没有想出如何让另一个远离另一个。正则表达式匹配一个字符串,但只有当另一个字符串不存在于同一行上的任何地方

使用https://regex101.com/我尝试了几十个搜索字符串。

这是我的搜索字符串的起点和一些尝试获取查找排除行上任何地方的AutoWidth的尝试。字符串2和3基本上是一样的东西,但我不知道还有什么要尝试的。我认为任何可以用于后视的东西都可以用于预测,但正如你所看到的,我甚至不能在后面工作。

(?<! AutoWidth="false") width="\d*"(?! AutoWidth="false") 
(?<! AutoWidth="false").*? width="\d*"(?! AutoWidth="false") 
(?<! AutoWidth="false")[0-9a-zA-Z" =]*? width="\d*"(?! AutoWidth="false") 

我卡住了,把正在躲避我AutoWidth和宽度之间的距离。

这是我的目标

1-> <column name="Selected" AutoWidth="false" IsEditable="true" datatype="bool" width="20"/> 
2-> <column width="40" AutoWidth="false" name="ExternalIdOrEmpty" index="XIDname" sort="true"/> 
3-> <column width="40" name="Tax Rate" index="TRname" sort="true" AutoWidth="false"/> 
4-> <column width="40" name="Total Tax" index="TTname" sort="true"/> 
5-> <column name="Tax Deductible" index="TDname" sort="true"/> 

我想找到包含

宽度的所有行= “\ d *”

,但不包含

AutoWidth = “\ d *”

在同一行上的任何地方。

这意味着只有第4行在上面的示例中符合我的标准。

UPDATE:

我愿意使用任何其他工具,将完成这项工作。所以XSLT等都很好。唯一的要求是,该工具通常可在Windows,Linux,Mac上使用,AND既可以是开源的,也可以是免费的,也是众所周知的。

完整的XML是巨大的。这里的编辑功能限制为30,00个字符,但这里有一个很好的示例。

<?xml version="1.0" encoding="utf-8" ?> 
<spread> 
    <ViewPatientOutboundReferralFilter> 
    <FindColumn name="ViewUid" index="guid" visible="false" /> 
    <FindColumn name="Selected" caption=" " visible="true" IsEditable="true" datatype="bool"/> 
    <FindColumn name="PatientName" caption="Patient Name" visible="true" width="150" hyperlink="true" AutoWidth="false"/> 
    <FindColumn name="ReferToProviderName" caption="Provider" visible="true" AutoWidth="false" width="150" hyperlink="true"/> 
    <FindColumn name="ReferredToMedicalServicesProviderName" caption="Medical Services Provider" visible="true" width="150" hyperlink="true"/> 
    <FindColumn name="ProviderRole" caption="Provider Role" visible="true" width="80" hyperlink="true"/> 
    <FindColumn name="StatusName" caption="Current Status" visible="true" width="100" hyperlink="true"/> 
    <FindColumn name="ServiceSiteName" caption="Service Site" visible="true"/> 
    <FindColumn name="VisitDate" caption="Visit Date" visible="true" width="90" datatype="date"/> 
    <FindColumn name="AppointmentDate" caption="Appointment Date" visible="true" datatype="datetime" width="90"/> 
    <FindColumn name="Notes" caption="Comments" visible="true" width="120"/> 
    <FindColumn name="AppointmentNotes" caption="Referral Notes" visible="true" width="120"/> 
    <FindColumn name="DisplayName" visible="false" index="name" /> 
    <FindColumn name="ProviderUid" visible="false" storeproperty="true" /> 
    <FindColumn name="VisitUid" visible="false" storeproperty="true" /> 
    <FindColumn name="CreatedDate" caption="Created Date" visible="true" datatype="date" width="90"/> 
    <FindColumn name="RequestingName" caption="Requesting Provider" visible="true" width="150" /> 
    </ViewPatientOutboundReferralFilter> 
    <FeeScheduleFeeAA rowcount="3"> 
    <column row="0" rowspan="3" caption="Code" width="50" name="Procedure.Code" sort="true" index="name" /> 
    <column row="0" rowspan="3" caption="Description" relwidth="100%" width="80" AutoWidth="false" name="Procedure.ShortDescription" sort="true" /> 
    <column row="0" rowspan="3" caption="Amount Allowed" width="60" AutoWidth="false" name="Fee" IsEditable="true" datatype="currency" /> 
    <column row="0" rowspan="3" caption="Global Period" width="40" AutoWidth="false" name="GlobalPeriodDays" IsEditable="true" datatype="number" decimalPlaces="0" minValue="0" maxValue="1000" /> 
    <column row="0" colspan="5" caption="Coinsurance" /> 
    <column row="1" colspan="2" caption="Insurance Percent" /> 
    <column row="2" caption=" " width="30" AutoWidth="false" name="RadioInsurancePercent" IsEditable="true" datatype="radio" radioOrientation="vertical" radioItems=" " /> 
    <column row="2" caption="Value" width="70" AutoWidth="false" name="InsurancePercent" IsEditable="true" datatype="number" decimalPlaces="0" minValue="0" maxValue="100" /> 
    <column row="1" colspan="2" caption="Insurance Plan" /> 
    <column row="2" caption="PCP/Specialist" width="95" AutoWidth="false" name="RadioInsurancePlanPhysician" IsEditable="true" datatype="radio" radioOrientation="vertical" radioItems=" " /> 
    <column row="2" caption="Other" width="55" AutoWidth="false" name="RadioInsurancePlanOther" IsEditable="true" datatype="radio" radioOrientation="vertical" radioItems=" " /> 
    <column row="1" rowspan="2" caption="Copay Amount" width="70" AutoWidth="false" name="FixedCopayAmount" datatype="currency" IsEditable="true" /> 
    <column row="0" rowspan="3" caption="Contract Type" width="55" AutoWidth="false" name="ContractTypeCode.Name" sort="true"/> 
    <column row="0" rowspan="3" caption="Family Planning" width="55" AutoWidth="false" name="FamilyPlanning" IsEditable="true" datatype="bool" /> 
    <column row="0" rowspan="3" caption="Alt Insurance Plan" width="55" AutoWidth="false" name="UseAlternateInsurancePlan" IsEditable="true" datatype="bool" /> 
    <column row="0" rowspan="3" caption="Edit Billing Rule" width="70" visible="false" IsEditable="true" datatype="CustomCellType" celltype="iMedica.Prm.Client.UI.BaseControls.Spread.PrmNeoCellImageButton,iMedica.Prm.Client.UI.BaseControls" ShowSortIndicator="false" ImageResourceName="iMedica.Prm.Client.UI.BaseControls.Icons.BillingRule.png" ImageResourceAssembly="iMedica.Prm.Client.UI.BaseControls" sort="false" /> 
    </FeeScheduleFeeAA> 
</spread> 
+3

了解如何使用HTML解析器和你的日子会更快乐。对于python:'beautifulsoup',对于java:'jsoup',对于php:'DOMDocument'等等...... –

+0

@PedroLobito他的html解析器是什么类型的?它可以帮助我解决我的XML问题吗? –

+1

xpath很简单。正则表达式解决方案看起来很难。 –

回答

6

这是XSLT中一个相当平凡的问题。给定一个结构良好的输入,诸如:

XML

<root> 
    <column name="Selected" AutoWidth="false" IsEditable="true" datatype="bool" width="20"/> 
    <column width="40" AutoWidth="false" name="ExternalIdOrEmpty" index="XIDname" sort="true"/> 
    <column width="40" name="Tax Rate" index="TRname" sort="true" AutoWidth="false"/> 
    <column width="40" name="Total Tax" index="TTname" sort="true"/> 
    <column name="Tax Deductible" index="TDname" sort="true"/> 
</root> 

以下样式表:

XSLT 1.0

<xsl:stylesheet version="1.0" 
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 
<xsl:output method="xml" version="1.0" encoding="UTF-8" indent="yes"/> 
<xsl:strip-space elements="*"/> 

<!-- identity transform --> 
<xsl:template match="@*|node()"> 
    <xsl:copy> 
     <xsl:apply-templates select="@*|node()"/> 
    </xsl:copy> 
</xsl:template> 

<xsl:template match="column/@width[not(../@AutoWidth)]"> 
    <xsl:copy/> 
    <xsl:attribute name="AutoWidth">False</xsl:attribute> 
</xsl:template> 

</xsl:stylesheet> 

将返回:

<?xml version="1.0" encoding="UTF-8"?> 
<root> 
    <column name="Selected" AutoWidth="false" IsEditable="true" datatype="bool" width="20"/> 
    <column width="40" AutoWidth="false" name="ExternalIdOrEmpty" index="XIDname" sort="true"/> 
    <column width="40" name="Tax Rate" index="TRname" sort="true" AutoWidth="false"/> 
    <column width="40" AutoWidth="False" name="Total Tax" index="TTname" sort="true"/> 
    <column name="Tax Deductible" index="TDname" sort="true"/> 
</root> 

这匹配没有兄弟AutoWidthwidth属性,将其复制并添加缺少的兄弟。在这里我有限的范围只column元素,但你可以扩展它从做任何元素:

<xsl:template match="@width[not(../@AutoWidth)]"> 
+0

这是一个很好的起点。有没有办法在应用修复程序时发出整个文档?我使用正则表达式的原因是因为我也可以使用替换方面,从而修复文档。我想我并不清楚这一点。 –

+0

@Dysmondad正是这样做的:所有没有被第二个模板匹配的节点都是由* identity transform *模板处理的 - 也就是*被复制的*。 –

+0

谢谢。这可以通过XML插件 - > Transform XML与Notepad ++协同工作。正是我需要的。 –

4

xpath是这样的://column[@width and not(@AutoWidth)]

说明:

  • //column发现所有<column ...>元件
  • [...]包含谓词
  • @width检查@widht属性的存在
  • not(@AutoWidth)检查缺席@AutoWidth属性。

我用freeformatter.com上的xpath tester进行测试。

我添加了一个<foo>元素以使其格式良好的XML。即这是实际的XML我用来测试:

<foo> 
    <column name="Selected" AutoWidth="false" IsEditable="true" datatype="bool" width="20"/> 
    <column width="40" AutoWidth="false" name="ExternalIdOrEmpty" index="XIDname" sort="true"/> 
    <column width="40" name="Tax Rate" index="TRname" sort="true" AutoWidth="false"/> 
    <column width="40" name="Total Tax" index="TTname" sort="true"/> 
    <column name="Tax Deductible" index="TDname" sort="true"/> 
</foo> 

那么,这是XPath://column[@width and not(@AutoWidth)]

它选择只有一个项目:<column index="TTname" name="Total Tax" sort="true" width="40"/>。我相信这是你需要的。

1

有使用grep另一个快速的解决方案。它需要一个bash外壳,例如来自windows的git-bash之一。

cat lines.txt | grep -P -v 'AutoWidth="[^"]*"' | grep -P 'width="[^"]*"' 

说明:

  • cat lines.txt - 这是你的数据来自
  • grep -P'使perl的语法简单起见
  • grep -v只保留不匹配的行
  • "[^"]*"匹配报价之间的所有内容,但不会在第一个报价后进一步发送

这是你的榜样数据结果:

4-> <column width="40" name="Total Tax" index="TTname" sort="true"/> 
相关问题