C#:基于视图数和随机数显示图像

C#:基于视图数和随机数显示图像,c#,visual-studio-2008,C#,Visual Studio 2008,我不确定在这篇文章中使用什么样的术语,所以请根据需要编辑标题 出于学习的目的,我正在尝试制作一个屏幕保护程序,随机显示指定文件夹中的图像。是的,Windows已经提供了这一功能,但同样是出于学习目的。虽然我更喜欢第一次就学会正确的方法,而不是重复一遍,重新学习如何正确地做事 现在我已经有了随机选择图像并显示它们的功能,等等。我想做的是根据特定图像的加载次数进行随机选择 例如: 图1:0视图(20%):1视图(19%) 图2:0视图(20%):0视图(24%) 图3:0视图(20%):1视图(19

我不确定在这篇文章中使用什么样的术语,所以请根据需要编辑标题

出于学习的目的,我正在尝试制作一个屏幕保护程序,随机显示指定文件夹中的图像。是的,Windows已经提供了这一功能,但同样是出于学习目的。虽然我更喜欢第一次就学会正确的方法,而不是重复一遍,重新学习如何正确地做事

现在我已经有了随机选择图像并显示它们的功能,等等。我想做的是根据特定图像的加载次数进行随机选择

例如:

图1:0视图(20%):1视图(19%)
图2:0视图(20%):0视图(24%)
图3:0视图(20%):1视图(19%)
图4:0视图(20%):2视图(14%)
图5:0视图(20%):0视图(24%) 这样,图像2和图像5下一步显示的可能性最大

我已经做了一段时间了,但我不确定到底出了什么问题,因为它只是抓住了列表中的下一张图片。我试图通过找到所有具有相同视图数的图片,然后通过该列表进行随机分组来对它们进行分组,但这似乎并不是最有效的方法。以下是我用于显示图片的代码:

Random rnd = new Random();  
string file = "";  
int totalViews = 0;  
List<string> array = new List<string>();  
void ShowPicture()  
{  
    array.Clear();  
    label1.Text = "";  
    foreach (Screen screen in Screen.AllScreens)  
    {  
        bool done = false;  
        while (!done)  
        {  
            int rand = rnd.Next(100), total;  
            foreach (string info in files.Keys)  
            {  
                total = (100 / files.Count) - (files[info] * (files.Count - 1)) + totalViews;  
                if (total >= rand)  
                {  
                    foreach (string tmp in files.Keys) if (total >= files[tmp]) array.Add(tmp);  
                    label1.Text = "Percentage for image: " + total;  
                    done = true;  
                    break;  
                }  
            }  
        }  
        file = array[rnd.Next(array.Count)];  
        files[file]++;  
        totalViews++;  
        Image image = Image.FromFile(file);  
        pictureBox1.Image = image;  

        label1.Text += "\nTotal Views: " + totalViews;  
    }  
} 
Random rnd=new Random();
字符串文件=”;
int totalViews=0;
列表数组=新列表();
void ShowPicture()
{  
array.Clear();
标签1.Text=“”;
foreach(屏幕中的屏幕。所有屏幕)
{  
bool done=false;
而(!完成)
{  
int rand=rnd.下一个(100),总计;
foreach(files.Keys中的字符串信息)
{  
总计=(100/files.Count)-(files[info]*(files.Count-1))+totalview;
如果(总数>=兰特)
{  
foreach(files.Keys中的字符串tmp)if(total>=files[tmp])array.Add(tmp);
label1.Text=“图像百分比:”+总计;
完成=正确;
打破
}  
}  
}  
file=array[rnd.Next(array.Count)];
文件[文件]+;
totalViews++;
Image=Image.FromFile(文件);
pictureBox1.图像=图像;
标签1.Text+=“\n总视图:”+totalViews;
}  
} 

我希望这一点足够清楚,并提前表示感谢。

我认为你正在为自己做更多的工作

我不完全确定您的变量都做了什么,但这就是我解决问题的方法(为了清楚起见,删除了设置和错误检查代码等):


然后我们选择一个介于0和1之间的随机数(
rndChoice
)-这是我们选择的数字行中的位置。第二个循环只需找到位于数字行中该点的图像,该图像就会显示出来。

我认为您为自己做的工作比需要的要多

我不完全确定您的变量都做了什么,但这就是我解决问题的方法(为了清楚起见,删除了设置和错误检查代码等):


然后我们选择一个介于0和1之间的随机数(
rndChoice
)-这是我们选择的数字行中的位置。第二个循环只需找到位于数字行中该点的图像,然后显示该图像。

我在查看链接时找到了idee

基本上,排序列表时,将权重与随机数相乘

所以试试这个

List<KeyValuePair<string, decimal>> list = new List<KeyValuePair<string, decimal>>();

            for (int iItem = 0; iItem < 10; iItem++)
                list.Add(new KeyValuePair<string, decimal>(iItem.ToString(), iItem/10m));

            Random rnd = new Random();

            list.Sort(  delegate(KeyValuePair<string, decimal> item1, KeyValuePair<string, decimal> item2) 
                        {
                            if (item1.Value == item2.Value)
                                return 0;
                            decimal weight1 = 1 / (item1.Value == 0 ? 0.01m : item1.Value);
                            decimal weight2 = 1 / (item2.Value == 0 ? 0.01m : item2.Value);
                            return (weight1 * rnd.Next()).CompareTo(weight2 * rnd.Next()); 
                        });
            list.Reverse();
List List=新列表();
对于(int iItem=0;iItem<10;iItem++)
添加(新的KeyValuePair(iItem.ToString(),iItem/10m));
随机rnd=新随机();
list.Sort(委托(KeyValuePair项1、KeyValuePair项2)
{
if(item1.Value==item2.Value)
返回0;
十进制权重1=1/(item1.Value==0?0.01m:item1.Value);
十进制权重2=1/(项目2.Value==0?0.01m:item2.Value);
return(weight1*rnd.Next()).CompareTo(weight2*rnd.Next());
});
list.Reverse();

我在查看链接时找到了idee

基本上,排序列表时,将权重与随机数相乘

所以试试这个

List<KeyValuePair<string, decimal>> list = new List<KeyValuePair<string, decimal>>();

            for (int iItem = 0; iItem < 10; iItem++)
                list.Add(new KeyValuePair<string, decimal>(iItem.ToString(), iItem/10m));

            Random rnd = new Random();

            list.Sort(  delegate(KeyValuePair<string, decimal> item1, KeyValuePair<string, decimal> item2) 
                        {
                            if (item1.Value == item2.Value)
                                return 0;
                            decimal weight1 = 1 / (item1.Value == 0 ? 0.01m : item1.Value);
                            decimal weight2 = 1 / (item2.Value == 0 ? 0.01m : item2.Value);
                            return (weight1 * rnd.Next()).CompareTo(weight2 * rnd.Next()); 
                        });
            list.Reverse();
List List=新列表();
对于(int iItem=0;iItem<10;iItem++)
添加(新的KeyValuePair(iItem.ToString(),iItem/10m));
随机rnd=新随机();
list.Sort(委托(KeyValuePair项1、KeyValuePair项2)
{
if(item1.Value==item2.Value)
返回0;
十进制权重1=1/(item1.Value==0?0.01m:item1.Value);
十进制权重2=1/(项目2.Value==0?0.01m:item2.Value);
return(weight1*rnd.Next()).CompareTo(weight2*rnd.Next());
});
list.Reverse();

+1对于效率,我也有一个类似的答案(但我的答案很重,所以我甚至懒得贴出来),但是你再次向我证明了最简单的答案就在你面前你只是选择忽略它们:我认为我正确地实现了这种方法,但它是按顺序进行的,只进行一次,然后停止。你在使用什么循环
ShowPicture()
如上所述,应该始终返回不同的图像-它不应该“停止”,问题的一部分在于它不断导致权重为1.0或0.0。由于某种原因,它计算不正确。所以我把行改为:fileWeighting[I]=((double)totalViews-(double)fileViews[I])/(double)totalViews;虽然现在新的错误是它只是循环t
List<KeyValuePair<string, decimal>> list = new List<KeyValuePair<string, decimal>>();

            for (int iItem = 0; iItem < 10; iItem++)
                list.Add(new KeyValuePair<string, decimal>(iItem.ToString(), iItem/10m));

            Random rnd = new Random();

            list.Sort(  delegate(KeyValuePair<string, decimal> item1, KeyValuePair<string, decimal> item2) 
                        {
                            if (item1.Value == item2.Value)
                                return 0;
                            decimal weight1 = 1 / (item1.Value == 0 ? 0.01m : item1.Value);
                            decimal weight2 = 1 / (item2.Value == 0 ? 0.01m : item2.Value);
                            return (weight1 * rnd.Next()).CompareTo(weight2 * rnd.Next()); 
                        });
            list.Reverse();