# Find tags in text for replacement, my brute force solution

I have a text such as

string text = "Hi [img-2] tst[img-3] test ttteessstt grawr[img-1-800]tet";


I want to find img tags in the text and get their id (second value) and possibly the third value if it exists.

string text = "Hi [img-2] tst[img-3] test ttteessstt grawr[img-1-800]tet";

var th = new TagHandler(null);
var res = th.FindImgTags(text);

foreach(var tag in res)
{
Debug.WriteLine(string.Join(", ", tag.Tag, tag.Id, tag.Width));
}


The above code outputs this:

[img-2], 2, 0
[img-3], 3, 0
[img-1-800], 1, 800


This is my "find tags code". Its crude but gets the job done... Any suggestions on how to make this less verbose / brute

public List<ImgReplaceItem> FindImgTags(string data)
{
var result = new List<ImgReplaceItem>();

var pieces = data.Split(new string[] { "[img-" }, StringSplitOptions.RemoveEmptyEntries);
foreach (var item in pieces)
{
if (item.Contains(']'))
{
var backend = item.Split(new char[] { ']' }, StringSplitOptions.RemoveEmptyEntries);
var dataInside = backend[0];

var r = new ImgReplaceItem();
r.Tag = "[img-" + dataInside + "]";
var pid = -1;
if (dataInside.Contains('-'))
{
var widthParts = dataInside.Split(new char[] { '-' }, StringSplitOptions.RemoveEmptyEntries);
int.TryParse(widthParts[0], out pid);

if (widthParts.Count() > 1)
{
var width = -1;
int.TryParse(widthParts[1], out width);
r.Width = width;
}
}
else
{
int.TryParse(dataInside, out pid);
}
r.Id = pid;
}
}

return result;
}

• I have rolled back the last edit. Please see what you may and may not do after receiving answers. – Heslacher Sep 7 '16 at 6:54
• @Heslacher I thought I give the OP a chance to repair it by himself ;-) – t3chb0t Sep 7 '16 at 7:12
• @t3chb0t since when are we a firendly community ? ;-) Just kidding. Nevertheless by adding the link to meta the reasons for the rollback are more clear. – Heslacher Sep 7 '16 at 7:15
• Hmm, ok. Seems weird that I should post a new answer when the answer I would post is basically copy paste of @t3chb0t with minor edit for my purpose. But I guess that is a question for a different forum. I'll post the code as an answer when I get back to my dev machine again. – JensB Sep 7 '16 at 7:29
• @JensB since it's not identical it's perfectly fine to post it as a self-anser. otherwise new visitors might want to review your reviewed code - this would be very confusing to everyone - a vicious circle. – t3chb0t Sep 7 '16 at 7:33

This is a lot of code for such a simple task... but how about some regex:

string text = "Hi [img-2] tst[img-3] test ttteessstt grawr[img-1-800]tet";

var ids = Regex.Matches(
text,
@"$(?<tag>[a-z]+)-(?<id>\d+)(-(?<width>\d+))?$",
RegexOptions.IgnoreCase | RegexOptions.ExplicitCapture
)
.Cast<Match>()
.Select(m => new ImgReplaceItem
{
Tag = m.Groups["tag"].Value,
Id = m.Groups["id"].Value,
Width = m.Groups["width"].Success ? int.Parse(m.Groups["width"].Value) : 0
});


result:

Tag Id  Width

img 2   0
img 3   0
img 1   800


As to the code. I think it's well writen. There isn't actually much to correct if anything.

if (item.Contains(']'))

You could make it !item.Contains(']') and use the contintue to reduce nesting.