如何通过将 DateTime 正确转换为 Double,将 DateTime 锚定到 ASP 柱形图上的 X 坐标?

How can I anchor a DateTime to the X coordinate on an ASP Column Chart by properly converting it to a Double?

我正在尝试将 DateTime 对象锚定到 ASP 柱形图的 X 坐标,以便我可以在图表初始化时在柱上显示线条注释。我知道它需要是 Double 才能工作,我尝试使用 DateTime.Now.ToOADate() 以及 ToDouble() 和 DateTime.Ticks 属性,但是 none 他们中有工作。

这是我的代码 (MainForm.aspx.cs):

    void getChartData()
    {
        String ConString = ConfigurationManager.ConnectionStrings["cs"].ConnectionString;
        using (SqlConnection connection = new SqlConnection(ConString))
        {
            String SQLText = "select AvailDate,MW from MWAvailability2 where UnitName = @UnitName and Station = @StationName and AvailDate between @AvailFrom and @AvailTo";
            SqlCommand cmd = new SqlCommand(SQLText, connection);
            connection.Open();
            cmd.Parameters.AddWithValue("@UnitName", ddUnit.SelectedValue);
            cmd.Parameters.AddWithValue("@StationName", ddStation.SelectedValue);
            if (TextBoxFrom.Text.Length > 0)
                {    
                    cmd.Parameters.AddWithValue("@AvailFrom", TextBoxFrom.Text);
                }
            else
                {    
                    cmd.Parameters.AddWithValue("@AvailFrom", "01-01-1900");
                }
            if (TextBoxTo.Text.Length > 0)
                {   
                    cmd.Parameters.AddWithValue("@AvailTo", TextBoxTo.Text);
                }
            else
                {
                    cmd.Parameters.AddWithValue("@AvailTo", "01-01-2050");
                }

            if (TextBoxFrom.Text.Length > 0 && TextBoxTo.Text.Length > 0)   // Text in from, text in to
            {
                chartTitle.Text = "Station " + ddStation.SelectedValue + " " + ddUnit.SelectedValue + " From: " + TextBoxFrom.Text + " To: " + TextBoxTo.Text;
            }
            else if (TextBoxFrom.Text.Length > 0 && TextBoxTo.Text.Length == 0)     // Text in from, no text in to
            {
                chartTitle.Text = "Station " + ddStation.SelectedValue + " " + ddUnit.SelectedValue + " From: " + TextBoxFrom.Text + " To: 01/01/2050";
            }
            else if (TextBoxFrom.Text.Length == 0 && TextBoxTo.Text.Length > 0)     // No text in from, text in to
            {
                chartTitle.Text = "Station " + ddStation.SelectedValue + " " + ddUnit.SelectedValue + " From: 01/01/1900 " + " To: " + TextBoxTo.Text;
            }
            else if (TextBoxFrom.Text.Length == 0 && TextBoxTo.Text.Length == 0)     // No text in from, no text in to
            {
                chartTitle.Text = "Station " + ddStation.SelectedValue + " " + ddUnit.SelectedValue + " From: 01/01/1900 To: 01/01/2050";
            }



            SqlDataReader reader = cmd.ExecuteReader();

            while (reader.Read())
            {
                Series series = ColumnChart.Series["Series1"];

                if (reader.HasRows)
                {

                   series.Points.AddXY(reader["AvailDate"].ToString(), reader["MW"]);

                    TextAnnotation ta = new TextAnnotation();

                    ta.AnchorX = Convert.ToDouble(reader["AvailDate"]); // problem
                    ta.AnchorY = Convert.ToDouble(reader["MW"]);

                    ta.Text = "Station A";
                    ColumnChart.Annotations.Add(ta);




                }
                else
                {
                    Console.WriteLine("No rows found.");
                }
            }

        }
    }

当应该将文本注释锚定到 X 坐标的行显示 ta.AnchorX = Convert.ToDouble(reader["AvailDate"]); 时,我收到一条错误消息显示 "Invalid cast from 'DateTime' to 'Double'." 当我将其更改为 ta.AnchorX = Convert.ToDouble(reader["AvailDate"].ToString()); 时,错误告诉我 "Input string was not in a correct format."

如果有帮助,这里是 HomePage.aspx.cs 的代码,其中进行此转换显然不那么复杂:

     void getChartData()
    {
        DataSet ds = new DataSet();
        // Read the data from XML file into DataSet
        ds.ReadXml(Server.MapPath("~/MWAvailability2.xml"));
        // Specify the column that contains values for X-AXIS
        ColumnChart.Series["Series1"].XValueMember = "AvailDate";
        // Specify the column that contains values for Y-AXIS
        ColumnChart.Series["Series1"].YValueMembers = "MW";
        // Annotations?
        TextAnnotation ta = new TextAnnotation();
        var xv = Convert.ToDouble("AvailDate");
        var yv = Convert.ToDouble("MW");

        ta.AnchorX = xv;
        ta.AnchorY = yv;

        ta.Text = "Station A";
        ColumnChart.Annotations.Add(ta);


        // Set DataSet as the DataSource for the Chart control
        ColumnChart.DataSource = ds;
        // Finally call DataBind
        ColumnChart.DataBind();
    }

我认为错误很可能与 SQL reader 对象有关,但我不确定。我在这里尝试了类似问题的其他解决方案,其中一些已在上面列出,但其中 none 似乎适用于我的情况。

我很乐意提供我可能遗漏的任何其他信息,这些信息可能有助于更好地解释我的情况。任何可以帮助我解决这个问题的意见或建议将不胜感激。提前致谢!

我将尝试主要关注您的问题行,它应该会引导您朝着正确的方向前进...

ta.AnchorX = Convert.ToDouble(reader["AvailDate"]); // problem

这里的问题是您没有提供 DateTime 值。 SqlReader class 在使用索引器时总是返回对象,这意味着您实际上是在调用构造函数 Convert.ToDouble(object) 而不是 Convert.ToDouble(DateTime)Convert class 正在抑制编译器错误,因为存在方法调用的匹配项,但不是您期望的匹配项。您可以通过尝试直接使用 reader["AvailDate"] 分配变量 AnchorX 来确认这一点。它会告诉您强制转换无效,因为如果没有显式强制转换,对象不能存储在更派生的类型中。如果您将 ToString() 附加到 reader(["AvailDate"]),这同样会调用 Convert.ToDouble(String)。如果存储在 SQL 数据库中的类型确实是 DateDateTime 的类型,那么您可以简单地指定一个转换。

试试这个:

ta.AnchorX = Convert.ToDouble((DateTime)reader["AvailDate"]); // solution?

更新

@Quantic 提醒我仍然抛出 InvalidCastException,而转换仍然是必要的,因为我最初的假设是它将在运行时失败。进一步检查 MSDN Convert.ToDouble(DateTime) 不受支持,将失败:

Return Value Type: System.Double This conversion is not supported. No value is returned.

https://msdn.microsoft.com/en-us/library/hfdd1sd9(v=vs.110).aspx

正确的调用确实是...

ta.AnchorX = ((DateTime)reader["AvailDate"]).ToOADate();