2

如果我问一个太明显的问题,我是一个新手程序员,所以提前抱歉。

我用 c#(WPF) 编程。

我有一些构建在这个结构中的字符串:

string str ="David went to Location 1 to have lunch";
string str2 ="Mike has to walk a mile facing north to reach Location 2";

我怎样才能以最优雅的方式将“位置 1”剪掉,用另一个字符串替换它(这可能会包含餐厅的名称,继续这个例子)?

我想过做类似的事情:

str.replace("Location 1", strRestaurantName);

但由于它应该是通用的(允许替换所有位置 x),它应该是str.indexof用来获取数字位置的东西(它可以是 1 到 20 之间的数字),只是我无法让它工作.. .

哦,不幸的是,我的老板不希望我使用正则表达式,否则我现在已经有了。

提前致谢。

4

4 回答 4

2

你也可以使用 Dictionary 像:

 Dictionary<string, string> Restaurants = new Dictionary<string, string>();

    public Form1()
    {
        InitializeComponent();
        Restaurants.Add("Location 1", "ABC Restaurant");
        Restaurants.Add("Location 2", "ABD Restaurant");
        Restaurants.Add("Location 3", "ABE Restaurant");
        Restaurants.Add("Location 4", "ABF Restaurant");
        Restaurants.Add("Location 5", "ABG Restaurant");
    }

    private void button1_Click(object sender, EventArgs e)
    {
      string str ="David went to Location 1 to have lunch";
      string str2 ="Mike has to walk a mile facing north to reach Location 2";

        MessageBox.Show( getRestaurant(str));
        // Result: David went to ABC Restaurant to have lunch

        MessageBox.Show( getRestaurant(str2));
        // Result: Mike has to walk a mile facing north to reach ABD Restaurant
    }

    private String getRestaurant(String msg)
    {
        String restaurantName = "";
        foreach (String loc in Restaurants.Keys)
        {
            if (msg.Contains(loc))
            {
                restaurantName = msg.Replace(loc, Restaurants[loc]);
                break;
            }
        }
        return  String.IsNullOrEmpty(restaurantName) ? msg : restaurantName;
    }

你也可以使用LINQ来缩短这样的getRestaurant方法:

    private String getRestaurant(String msg)
    {
        String restaurantName = Restaurants.Keys.FirstOrDefault<String>(v => msg.Contains(v));
        return String.IsNullOrEmpty(restaurantName) ? msg : msg.Replace(restaurantName, Restaurants[restaurantName]);
    }
于 2013-05-20T06:31:57.027 回答
1

如何使用格式化?这样的事情应该可以解决问题:

string locationString = "some string";
string.Format("David went to {0} to have lunch", locationString);

这将导致以下句子:David went to some string to have lunch

当然,您可以根据需要添加任意数量的字符串,并且可以通过反复使用相同的变量编号来复制相同的字符串(例如:David went to {0} and {0} to have lunch这将期望只有一个string将插入到{0}位置。

于 2013-05-20T06:00:31.630 回答
0

就像其他人所说的那样,正则表达式确实是正确的解决方案,但我们基本上可以做正则表达式在内部做的事情。

注意:我没有测试,甚至没有编译过这段代码。这应该匹配Location (\d+)

string ReplaceLocation(string input, IList<string> replacements)
{
    string locString = "Location ";
    int matchDigitStart = 0;
    int matchDigitEnd = 0;
    int matchStart = 0;

    do{
        matchStart = input.IndexOf(locString, matchDigitStart);
        if(matchStart == -1)
        {
            throw new ArgumentException("Input string did not contain Location identifier", "input");
        }

        matchDigitStart = matchStart + locString.Length;
        matchDigitEnd = matchDigitStart;
        while(matchDigitEnd < input.Length && Char.IsDigit(input[matchDigitEnd]))
        {
            ++matchDigitEnd;
        }

    } while (matchDigitEnd == matchDigitStart);


    int locationId = int.Parse(input.Substring(matchDigitStart, matchDigitEnd - matchDigitStart));
    if(locationId > replacements.Count || locationId == 0 )
    {
        throw new ArgumentException("Input string specified an out-of-range location identifier", "input");
    }

    return input.Substring(0, matchStart) + replacements[locationId - 1] + input.Substring(matchDigitEnd);
}
于 2013-05-20T07:55:33.743 回答
0

你在正确的轨道上。我在想:

1)您想在列表中参数化“位置 1=这家餐厅”、“位置 2=那个地方”等:

http://www.dotnetperls.com/list

http://www.dotnetperls.com/split

2)您的代码将循环遍历每个字符串的每个列表项。或者也许循环直到找到匹配项。

3) 如果可能,更好的事件方法可能是使用 C# 占位符,而不是发明自己的“位置 N”语法,例如str.Format("David went to {0} to have lunch", strRestaurantName);,或str.Format("David went to {0} to have lunch, then Mike has to walk a mile facing north to reach {1}", strRestaurantName, strHikingLocation);

于 2013-05-20T06:01:04.327 回答