আপনি কীভাবে এক্সএমএলসিরাইজার ব্যবহার করে কোনও স্ট্রিংকে সিডিএটিএ হিসাবে সিরিয়ালাইজ করবেন?


91

। নেট এক্সএমএলসিরালাইজার ব্যবহার করে কোনও স্ট্রিংকে সিডিএটিআইএলাইজ করতে কোনও ধরণের অ্যাট্রিবিউটের মাধ্যমে কি সম্ভব?


4
দুটি উত্তর সম্পর্কে লক্ষ্য করার মতো একটি বিষয় হ'ল CDataContentআপনি যদি কেবল এক্সএমএল পড়েন তবে আপনার প্রয়োজন হবে না । XmlSerializer.Deserializeএটি আপনার জন্য স্বয়ংক্রিয়ভাবে পাঠ্যে পরিণত হবে।
ক্রিস এস

উত্তর:


62
[XmlRoot("root")]
public class Sample1Xml
{
    internal Sample1Xml()
    {
    }

    [XmlElement("node")]
    public NodeType Node { get; set; }

    #region Nested type: NodeType

    public class NodeType
    {
        [XmlAttribute("attr1")]
        public string Attr1 { get; set; }

        [XmlAttribute("attr2")]
        public string Attr2 { get; set; }

        [XmlIgnore]
        public string Content { get; set; }

        [XmlText]
        public XmlNode[] CDataContent
        {
            get
            {
                var dummy = new XmlDocument();
                return new XmlNode[] {dummy.CreateCDataSection(Content)};
            }
            set
            {
                if (value == null)
                {
                    Content = null;
                    return;
                }

                if (value.Length != 1)
                {
                    throw new InvalidOperationException(
                        String.Format(
                            "Invalid array length {0}", value.Length));
                }

                Content = value[0].Value;
            }
        }
    }

    #endregion
}

9
আমার কাছে এটি সবচেয়ে মার্জিত সমাধানের মতো বলে মনে হচ্ছে না। এটি কি এটি করার একমাত্র সম্ভাব্য উপায়?
জামসাহারভেহে

4
আমি মনে করি এটি সম্পাদন করার একমাত্র উপায় এটি আমি এই বিষয়টি অন্য কোথাও দেখেছি এবং সর্বদা একই উত্তর। ফিলিপের উদাহরণটি একটু পরিচ্ছন্ন তবে একই ধারণা। শুধুমাত্র অন্যান্য উপায় আমি জানি আপনার নিজের <a href=" msdn.microsoft.com/en-us/library/... বাস্তবায়ন হয়> একটি বর্গ যে CDATA বিষয়বস্তু প্রতিনিধিত্ব করে।
csharptest.net

আমি একই জিনিসটি করতে চেয়েছিলাম কারণ এটি দেখে মনে হচ্ছে যে স্ট্রিংগুলি সংরক্ষণ করার মতো সিডিএটিএ প্রক্রিয়াকরণের সময় কম বলে মনে হচ্ছে, এর সাথে আমরা কেবল 'পঠন / লেখার স্ট্রিং'কে যেমন করতে পারি'। এক্সএমএল ডকুমেন্ট / এক্সএমএলসিসিডিটাসেকশন উদাহরণগুলি জড়িত কত ব্যয়বহুল?
তিশমা

এবং সম্পূর্ণ বৈশিষ্ট্যযুক্ত জিনিসটি তাই আমরা ডোমেন মডেল ক্লাসগুলি সিরিয়ালাইজেশনের যুক্তি বিশদ থেকে পরিষ্কার রাখতে সক্ষম হয়েছি। নোংরা উপায় যদি একমাত্র উপায় হয় তবে এটি দুঃখজনক।
তিশমা

4
পৃষ্ঠার সামান্য দূরে ফিলিপের সমাধান করা একটি পরিশ্রমী কাজ।
কার্ল

99
[Serializable]
public class MyClass
{
    public MyClass() { }

    [XmlIgnore]
    public string MyString { get; set; }
    [XmlElement("MyString")]
    public System.Xml.XmlCDataSection MyStringCDATA
    {
        get
        {
            return new System.Xml.XmlDocument().CreateCDataSection(MyString);
        }
        set
        {
            MyString = value.Value;
        }
    }
}

ব্যবহার:

MyClass mc = new MyClass();
mc.MyString = "<test>Hello World</test>";
XmlSerializer serializer = new XmlSerializer(typeof(MyClass));
StringWriter writer = new StringWriter();
serializer.Serialize(writer, mc);
Console.WriteLine(writer.ToString());

আউটপুট:

<?xml version="1.0" encoding="utf-16"?>
<MyClass xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
  <MyString><![CDATA[<test>Hello World</test>]]></MyString>
</MyClass>

এটি কেবল আমার দিনটি বাঁচিয়েছে। ধন্যবাদ.
রবার্ট

4
// আপনার যদি খালি সিডিএটিএ প্রয়োজন হয় তবে যদি উত্স মানটি ব্যতিক্রম এড়াতে নাল হয় তবে আপনি ডিফল্ট সেট করতে পারেন। XmlDocument().CreateCDataSection(MyString ?? String.Empty);
অসেরেওয়্যার

@ pr0gg3r এটিও কি একই বস্তুতে ডিসরিয়ালাইজিংয়ের অনুমতি দেয়? এতে আমার সমস্যা হচ্ছে
মার্টিন

<মাইক্লাস> <! [সিডিএটিএ [<টেস্টে> হ্যালো ওয়ার্ল্ড </ strong>]]> << মাই ক্লাস> এর মতো পাঠ্য মান হিসাবে (এবং কোনও উপাদান হিসাবে নয়) হিসাবে সিডিএটিএ কীভাবে তৈরি করবেন?
এমকো

4
কেবলমাত্র <emptyfield> << পিডিডিএডিটিএডিএলডিআরএলটি </ emmptyfield> আউটপুট করার চেয়ে খালি / নাল মানগুলি হ্যান্ডেল করতে সক্ষম হতে হবে
8:44 এ নীল

91

জন স্যান্ডার্স যেভাবে পোস্ট করেছেন সেগুলি ছাড়াও, আপনি সরাসরি প্রকার হিসাবে একটি এক্সএমএলসিডিটাএসেকশন ব্যবহার করতে পারেন , যদিও এটি প্রায় একই জিনিসটিতে সিদ্ধ হয়:

private string _message;
[XmlElement("CDataElement")]
public XmlCDataSection Message
{  
    get 
    { 
        XmlDocument doc = new XmlDocument();
        return doc.CreateCDataSection( _message);
    }
    set
    {
        _message = value.Value;
    }
}

4
ফিলিপ, এই deserialization জন্য কাজ করে? আমি নোটগুলি দেখছি যা বলছে যে সেটারটি একটি এক্সএমএলেক্সট মান পাবে।
জন স্যান্ডার্স

4
@John বিযয়ক - এটা আসলে deserialization সময় সেটার, যা কি .Value থেকে কল জন্য সেটার হয় একটি XmlCharacterData মান গ্রহণ করে (আমি মূলত এটা ToString () মেমরি থেকে যেমন ছিল, কিন্তু যে ভুল ছিল।)
ফিলিপ Rieck

4
@ ফিলিপিরিক যদি আমাদের কোনও সিডিটা সেকশনের চারপাশে একটি কাস্টম অবজেক্ট আবশ্যক হয় তবে কী হবে। সিডিটাসেকশন তৈরি করুন স্ট্রিং গ্রহণ করে।
জেপেলিন

ধন্যবাদ! সবচেয়ে সহজ সমাধান। আমার জন্য ভাল কাজ করে।
আন্তোনিও রদ্রিগেজ

43

ক্লাসে সিরিয়াল করা হবে:

public CData Content { get; set; }

এবং সিডিটা ক্লাস:

public class CData : IXmlSerializable
{
    private string _value;

    /// <summary>
    /// Allow direct assignment from string:
    /// CData cdata = "abc";
    /// </summary>
    /// <param name="value">The string being cast to CData.</param>
    /// <returns>A CData object</returns>
    public static implicit operator CData(string value)
    {
        return new CData(value);
    }

    /// <summary>
    /// Allow direct assignment to string:
    /// string str = cdata;
    /// </summary>
    /// <param name="cdata">The CData being cast to a string</param>
    /// <returns>A string representation of the CData object</returns>
    public static implicit operator string(CData cdata)
    {
        return cdata._value;
    }

    public CData() : this(string.Empty)
    {
    }

    public CData(string value)
    {
        _value = value;
    }

    public override string ToString()
    {
        return _value;
    }

    public System.Xml.Schema.XmlSchema GetSchema()
    {
        return null;
    }

    public void ReadXml(System.Xml.XmlReader reader)
    {
        _value = reader.ReadElementString();
    }

    public void WriteXml(System.Xml.XmlWriter writer)
    {
        writer.WriteCData(_value);
    }
}

একটি যাদুমন্ত্র মত কাজ করে. ধন্যবাদ.
লিওনেল সান্চস সিলভা

4
এই উত্তরটি আরও স্বীকৃতির দাবিদার। যদিও, কাস্টমাইজড সিডিটা টাইপটিতে আর সেই সুবিধাজনক অন্তর্নির্মিত পদ্ধতি নেই যা সিস্টেম.স্ট্রিং টাইপ উপভোগ করে।
লিওনেট চেন

চমৎকার তারপর প্রথম উত্তর
Hsin-Yu চেন

উত্তর দুর্দান্ত কাজ করে। এটি লজ্জার বিষয় যে এক্সএমএলিমেন্ট স্ট্রিং ফিল্ডে কাজ করে না, তারপরে আপনি কেবল একটি সিডিটা টাইপ যুক্ত করতে পারেন তবে যাই হোক না কেন ...
jjxtra

পারফেক্ট! ধন্যবাদ!
রায়

5

আমার একই রকম প্রয়োজন ছিল তবে আলাদা আউটপুট ফর্ম্যাটটির প্রয়োজন ছিল - আমি নোডে একটি বৈশিষ্ট্য চেয়েছিলাম যাতে সিডিএটিএ রয়েছে। আমি নিজের তৈরি করতে উপরের সমাধানগুলি থেকে কিছুটা অনুপ্রেরণা নিয়েছি। সম্ভবত এটি ভবিষ্যতে কাউকে সহায়তা করবে ...

public class EmbedScript
{
    [XmlAttribute("type")]
    public string Type { get; set; }

    [XmlText]
    public XmlNode[] Script { get; set; }

    public EmbedScript(string type, string script)
    {
        Type = type;
        Script = new XmlNode[] { new XmlDocument().CreateCDataSection(script) };
    }

    public EmbedScript()
    {

    }
}

সিরিয়ালাইজড হওয়ার জন্য প্যারেন্ট অবজেক্টে আমার নীচের সম্পত্তি রয়েছে:

    [XmlArray("embedScripts")]
    [XmlArrayItem("embedScript")]
    public List<EmbedScript> EmbedScripts { get; set; }

আমি নিম্নলিখিত আউটপুট পেতে:

<embedScripts>
    <embedScript type="Desktop Iframe">
        <![CDATA[<div id="play_game"><iframe height="100%" src="http://www.myurl.com" width="100%"></iframe></div>]]>
    </embedScript>
    <embedScript type="JavaScript">
        <![CDATA[]]>
    </embedScript>
</embedScripts>

4
আমার ঠিক এটি করা দরকার ছিল। ধন্যবাদ!!
লিউস থেরিন

4

আমার ক্ষেত্রে আমি মিশ্র ক্ষেত্রগুলি ব্যবহার করছি, কিছু সিডিটিএ কিছু না, কমপক্ষে আমার জন্য নিম্নলিখিত সমাধানটি কাজ করছে ...

সর্বদা মান ক্ষেত্রটি পড়ে, আমি সিডিটিএ বা কেবল সরল পাঠ্য নির্বিশেষে বিষয়বস্তুগুলি পাচ্ছি।

    [XmlElement("")]
    public XmlCDataSection CDataValue {
        get {
            return new XmlDocument().CreateCDataSection(this.Value);
        }
        set {
            this.Value = value.Value;
        }
    }

    [XmlText]
    public string Value;

কখনও না থেকে ভাল।

চিয়ার্স


কল্পনাপ্রসূত - আমার এই অনুভূতিটি আমার বেশিরভাগ সময়কে বাঁচিয়েছে! তথ্যের জন্য আমি মানগুলিতে [XMLIgnore] বৈশিষ্ট্যটি ব্যবহার করেছি
d219

এটি কীভাবে pr0gg3r এর উত্তরের চেয়ে আলাদা ?
রাফিন

2

এই প্রয়োগে আপনার এনকোড করা স্ট্রিংয়ের মধ্যে নেস্টেড সিডিএটিএ প্রক্রিয়া করার ক্ষমতা রয়েছে (জন স্যান্ডার্সের মূল উত্তরের উপর ভিত্তি করে)।

উদাহরণস্বরূপ, ধরুন আপনি নিম্নলিখিত আক্ষরিক স্ট্রিংটি সিডিএটি তে এনকোড করতে চেয়েছিলেন:

I am purposefully putting some <![CDATA[ cdata markers right ]]> in here!!

আপনি ফলাফলের ফলাফলটি এরকম কিছু দেখতে চাইবেন:

<![CDATA[I am purposefully putting some <![CDATA[ cdata markers right ]]]]><![CDATA[> in here!!]]>

স্ট্রিং উপর নিম্নলিখিত বাস্তবায়ন ইচ্ছা লুপ, দৃষ্টান্ত বিভক্ত ...]]>...মধ্যে ...]]এবং >...এবং প্রতিটি জন্য পৃথক CDATA বিভাগগুলি তৈরি করুন।

[XmlRoot("root")]
public class Sample1Xml
{
    internal Sample1Xml()
    {
    }

    [XmlElement("node")]
    public NodeType Node { get; set; }

    #region Nested type: NodeType

    public class NodeType
    {
        [XmlAttribute("attr1")]
        public string Attr1 { get; set; }

        [XmlAttribute("attr2")]
        public string Attr2 { get; set; }

        [XmlIgnore]
        public string Content { get; set; }

        [XmlText]
        public XmlNode[] CDataContent
        {
            get
            {
                XmlDocument dummy = new XmlDocument();
                List<XmlNode> xmlNodes = new List<XmlNode>();
                int tokenCount = 0;
                int prevSplit = 0;
                for (int i = 0; i < Content.Length; i++)
                {
                    char c = Content[i];
                    //If the current character is > and it was preceded by ]] (i.e. the last 3 characters were ]]>)
                    if (c == '>' && tokenCount >= 2)
                    {
                        //Put everything up to this point in a new CData Section
                        string thisSection = Content.Substring(prevSplit, i - prevSplit);
                        xmlNodes.Add(dummy.CreateCDataSection(thisSection));
                        prevSplit = i;
                    }
                    if (c == ']')
                    {
                        tokenCount++;
                    }
                    else
                    {
                        tokenCount = 0;
                    }
                }
                //Put the final part of the string into a CData section
                string finalSection = Content.Substring(prevSplit, Content.Length - prevSplit);
                xmlNodes.Add(dummy.CreateCDataSection(finalSection));

                return xmlNodes.ToArray();
            }
            set
            {
                if (value == null)
                {
                    Content = null;
                    return;
                }

                if (value.Length != 1)
                {
                    throw new InvalidOperationException(
                        String.Format(
                            "Invalid array length {0}", value.Length));
                }

                Content = value[0].Value;
            }
        }
    }
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.