C#求样区数据的均值和协方差,利用交错数组
遥感多光谱影像是指对同一地区同时在若干个波段进行成像。为了分析的需要,有时需要在多光谱影像中选取一个范围进行分析,该范围称为一个样区。样区边界相同,但对应的每个波段的影像数据不一样。如下图所示。
题目:已知某多光谱遥感影像一个样区的数据。分别计算该样区数据的均值向量和协方差矩阵。
计算公式如下:
1)均值向量:
2)协方差矩阵:
式中: 表示第i个波段样区的第k个像元值,N为样区像元总个数。
考试说明:
1、请考生先在d盘建立一个子目录,所有考试内容都保存在该目录。子目录命名格式如下:
考号_姓名
注意:对于没有建立相应子目录或考试内容没有保存在该目录所产生的一切后果由考生自负。
2、数据格式说明如下:
样本数据以文本形式放在文件的d:\data.txt中,格式如下:
波段数
样本数
第一波段样本数据
第二波段样本数据
…
3、编程要求:
1、 读出样本数据;
2、 分别编写计算样区的均值向量和协方差矩阵的子函数;
3、 主函数完成输入输出及子函数调用功能;
4、 编译运行并将计算结果存入result.txt文件;
5、程序结构清晰,注释清楚。
自己造了一个数据:boduan.txt
3
36
12 12.5 16.3 27 28 19
13 13.4 17.9 24 71.9 88
15 13.4 17 29 77 88
15 14 18 30 78 90
14.4 12 21 30 78 89
14 14.5 18.5 31 77 90
13 13.4 17.9 24 71.9 88
12 12.5 16.3 27 28 19
15 13.4 18 29 77 88
14.4 12 21 30 78 89
15 14 18 30 78 90
14 14.5 18.5 31 77 90
12 12.5 16.3 27 28 19
15 13.4 18 29 77 88
13 13.4 17.9 24 71.9 88
14 14.5 18.5 31 77 90
15 14 18 30 78 90
14.4 12 21 30 78 89
代码如下:
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.IO;
namespace bdxc
{
class Program
{
//求均值
static double Ave(double[] data)
{
double sum = 0;
for (int i = 0; i < data.Length; i++)
{
sum += data[i];
}
double ave = sum / data.Length;
return ave;
}
//求协方差
static double[,] Covar(double[][] data,double[] ave)
{
double[,] covar = new double[ave.Length, ave.Length];
for (int i = 0; i < ave.Length; i++)
{
for (int j = 0; j < ave.Length ;j++ )
{
double sum=0;
for(int k=0; k < data[i].Length ;k++ )
{
double temp=(data[i][k]-ave[i])*(data[j][k]-ave[j]);
sum+=temp;
}
covar[i,j]=sum/data[i].Length;
}
}
return covar;
}
static void Main(string[] args)
{
//声明文件路径
string txtpath = (@"D:\C#练习\boduan.txt");
string resultpath = (@"D:\C#练习\boduanresult.txt");
//读取文件
FileStream fs = new FileStream(txtpath, FileMode.Open);
StreamReader sr = new StreamReader(fs);
//拆分字符串str
string temp=null;
string str = null;
while ((temp = sr.ReadLine()) != null)
{
str += temp+" ";
}
string[] delimiter={" "," "," "};
string[] strs = str.Split(delimiter, StringSplitOptions.RemoveEmptyEntries);
double[] strd = new double[strs.Length-2];
int wavenum = 0, xynum = 0;
//获取波段数wavenum,样区像元个数xynum,样区数据strd[]
for(int i=1;i<strs.Length;i++)
{
if (i<2)
{
wavenum = Convert.ToInt32(strs[0]);
xynum = Convert.ToInt32(strs[1]);
}
else
{
strd[i-2]=Convert.ToDouble(strs[i]);
}
}
//交错数组初始化
double[][] data = new double[wavenum][];
for (int i = 0; i < wavenum; i++)
{
data[i] = new double[xynum];
}
//获取不同波段数据data[][],例如:data[0]为波段1数据
for (int i = 0; i < wavenum; i++)
{
for (int j = xynum * i,k=0; j < xynum * (i + 1)&&k<xynum; j++,k++)
{
data[i][k] = strd[j];
}
}
//调用方法求均值
double[] ave= new double[wavenum];
for (int i = 0; i < wavenum; i++)
{
ave[i] = Ave(data[i]);
}
//调用方法求协方差
double[,] covar = Covar(data, ave);
//写入文件
FileStream fs1 = new FileStream(resultpath, FileMode.Create);
StreamWriter sw = new StreamWriter(fs1);
sw.Write("样区数据均值向量为:");
foreach (double d in ave)
{
sw.Write(d);
sw.Write(" ");
}
sw.WriteLine();
sw.Write("样区数据协方差阵为:"+"\r\n");
for (int i = 0; i < ave.Length ;i++ )
{
for (int j = 0; j < ave.Length; j++)
{
sw.Write(covar[i, j]);
sw.Write(" ");
}
sw.WriteLine();
}
sw.Close();
}
}
}