• 转帖 [C#][Silverlight]透過LINQ取得不重複的隨機數值


    日前在專案中有需要從題庫中隨機挑選題目的需求,加上最近在MSDN論壇看到有人在問隨機取得不重複的數值的問題,為了避免之後又不小心忘記這個方便的寫法,特別寫文章來紀錄一下。

    首先,請直接看這個範例(請別把這個範例當作明牌產生器喔!!槓龜我可不負責~少來了!):

    接著看看原始碼:

    MainPage.xaml
    
    <UserControl xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
      xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
      xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
      xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
      xmlns:theme="clr-namespace:System.Windows.Controls.Theming;assembly=System.Windows.Controls.Theming.ExpressionDark"
      xmlns:toolkit="http://schemas.microsoft.com/winfx/2006/xaml/presentation/toolkit"
      x:Class="SL_RandomWithLinq.MainPage" mc:Ignorable="d" d:DesignHeight="600" d:DesignWidth="800">
     <theme:ExpressionDarkTheme Background="{x:Null}" Foreground="#FF646464">
      <Border BorderThickness="2" CornerRadius="10" Margin="10" Background="White" BorderBrush="#FF646464">
       <Border.Effect>
        <DropShadowEffect />
       </Border.Effect>
       <Grid x:Name="LayoutRoot" Background="Transparent">
        <Grid.RowDefinitions>
         <RowDefinition Height="40" />
         <RowDefinition />
         <RowDefinition Height="Auto" />
        </Grid.RowDefinitions>
        <TextBlock HorizontalAlignment="Center" TextWrapping="Wrap" Text="Silverlight 透過Linq取亂數範例"
          VerticalAlignment="Center" FontSize="26.667" FontWeight="Bold" />
        <Rectangle Fill="#FF646464" Height="2" Margin="10,0" VerticalAlignment="Bottom" />
        <TextBlock HorizontalAlignment="Center" TextWrapping="Wrap" Text="第 00000 期大樂透得獎號碼"
          VerticalAlignment="Top" FontSize="32" FontWeight="Bold" Grid.Row="1" Margin="10,10,0,0"
          FontStyle="Italic" Foreground="#FFFFC700">
         <TextBlock.Effect>
          <DropShadowEffect ShadowDepth="1" />
         </TextBlock.Effect></TextBlock>
        <toolkit:WrapPanel x:Name="wrpNumbers" Margin="10,60,10,10" Grid.Row="1">
         <toolkit:WrapPanel.Effect>
          <DropShadowEffect Opacity="0.5" ShadowDepth="1" />
         </toolkit:WrapPanel.Effect>
        </toolkit:WrapPanel>
        <Button x:Name="btnRandom" Content="重新開獎" HorizontalAlignment="Center" Grid.Row="3"
          VerticalAlignment="Center" Margin="0,5,0,10" Padding="10,5" FontSize="16"
          Click="btnRandom_Click" />
       </Grid>
      </Border>
     </theme:ExpressionDarkTheme>
    </UserControl>
    

    CodeBehind:

    MainPage.xaml.cs
    
    using System;
    using System.Linq;
    using System.Windows;
    using System.Windows.Controls;
    using System.Windows.Media;
    namespace SL_RandomWithLinq
    {
        public partial class MainPage : UserControl
        {
            public MainPage()
            {
                InitializeComponent();
                for( int i = 1 ; i <= 49 ; i++ )
                {
                    this.wrpNumbers.Children.Add( new TextBlock
                                                    {
                                                        Text = i.ToString( "00" ) ,
                                                        Foreground = new SolidColorBrush { Color = Colors.Gray } ,
                                                        FontSize = 32 ,
                                                        Width = 80 ,
                                                        Margin = new Thickness( 5 ) ,
                                                        TextAlignment = TextAlignment.Center ,
                                                    } );
                }
            }
            private void btnRandom_Click( object sender , RoutedEventArgs e )
            {
                //重置所有號碼為灰色
                this.wrpNumbers.Children.OfType<TextBlock>().ToList().ForEach( t => t.Foreground = new SolidColorBrush { Color = Colors.Gray } );
                //將數值打亂之後透過Take方法取出前6個值
                var result = Enumerable.Range( 1 , 49 ).OrderBy( n => n * n * ( new Random() ).Next() ).Take( 6 );
                //將被挑選出來的號碼改為紅色
                result.ToList().ForEach( i => this.wrpNumbers.Children.OfType<TextBlock>().ElementAt( i - 1 ).Foreground = new SolidColorBrush { Color = Colors.Red } );
            }
    
        }
    }
    

    透過LINQ,真的很威能啊!!原本可能得要透過迴圈才能完成的動作,改由LINQ來實作,就真的只需要一行!!沒錯!!一行!!

    不過,您可能會擔心取出來的亂數不夠亂--別擔心,這個寫法是有參考洋人墨水的(參考連結在此:Generating random sequences with LINQ )~

    Posted by demo on 2011/10/15 下午 10:32 回覆
    我比較習慣直接用 Guid 去排
    var result = Enumerable.Range( 1 , 49 ).OrderBy( d=>Guid.NewGuid() ).Take( 6 );
  • 相关阅读:
    Python中匿名函数的应用
    Python中界面阻塞情况的解决方案
    Python中的协程,gevent模块
    Python中的进程和线程
    Python中的正则表达式用法
    Jquery瀑布流效果(下篇)
    安卓不支持keypress事件
    让MAC OS也能使用LL LA L等LS的别名
    git 常用命令
    javascript中的apply与call
  • 原文地址:https://www.cnblogs.com/thanks/p/2350473.html
Copyright © 2020-2023  润新知