現在、fortranで大きな数値計算をしています。

そこで、計算回数が多く、その計算過程において大きい値と小さい値とを何回も計算していると誤差が次第に大きくなっていきます。

A=BとなるようにA(又はB)を求めるときの判別としてabs(A-B)<10**(x)
としています。

このxに-300ぐらいの値をいれ判別したいのですがそれは可能ですか?

もちろん計算には倍精度を使っていますがabs(A-B)が10**(-17)付近になると値が一定になってしまいます。これがfortranの限界なのでしょうか?

このQ&Aに関連する最新のQ&A

A 回答 (3件)

fotranで.尋常な方法ではないのですが.物理制限のみという演算をしたことがあります。


変数を整数配列にして.1桁を1配列に割り当てて.演算ルーチンを作成します。
三角関数や対数程度でしたらば.探せば.加減算で求めるプログラムも公開されていますから.開発は特に困難ではないでしょう。

私の場合には.マンマシンインターフェースとして.対話処理にしたことが災いし.プログラム領域が不足し.オーバーレイ構造にするためには.システム情報が必要となり.一般ユーザーであるために開発を断念しました。システム情報を操作するためには.特権ユーザーである必要があったためです。
    • good
    • 0

> A=BとなるようにA(又はB)を求めるときの判別としてabs(A-B)<10**(x)


> としています。

絶対誤差がいいんですかね。
相対誤差も検討してみてください。
    • good
    • 0

倍精度の有効桁数は16~17桁ですから、大体そこが精度の限界になります。



計算の誤差に詳しいページを示しておきますね。(参考URL)

参考URL:http://www.pu-toyama.ac.jp/joker/1999kouki/c8.htm
    • good
    • 0

このQ&Aに関連する人気のQ&A

お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!

このQ&Aと関連する良く見られている質問

Q実験の誤差について

誤差は主に系統誤差と偶然誤差に分けられますが、最終結果においては
普通これらの誤差をどのように扱うのでしょうか?

系統誤差と偶然誤差をそれぞれ算出した後、
・値が大きい方の誤差を最終的な「誤差」とする
・二つの誤差を足し合わせて最終結果としての「誤差」とする
・いずれも実験値の最終的な「誤差」として議論する
 (特に二つを足したり引いたりするわけでもなく、「統計誤差」「偶然誤差」を
  どちらも最終的な「誤差」として取り扱っていく)
のどれが一般的に行われてることなのでしょうか。それとも、また別の扱い方が
されているのでしょうか。

回答よろしくお願いいたします。

Aベストアンサー

この Wikipedia の記事に貼ってある画像がわかりやすいでしょう。

正確度と精度 - Wikipedia
http://ja.wikipedia.org/wiki/%E6%AD%A3%E7%A2%BA%E5%BA%A6%E3%81%A8%E7%B2%BE%E5%BA%A6

つまり、そもそも的の中心から外れた方向に向いている、というのが「系統誤差」(正確度・確度)、

狙いは定まっているけれども、毎回同じところに飛んでいかない、というのが「偶然誤差」(精度)、

というわけです。

系統誤差の存在は、「そもそも基準はどこか?」というのがわかっていないと、絶対的数値が求まりません。ですから、測定値では、基準物の測定結果が無い限りは、どれだけが系統誤差でどれだけが偶然誤差なのか、という分離ができないのです。

Qオブジェクト指向における「クラスA have a クラスB」の関係において,クラスBからクラスAのあるメンバ変数だけを触る方法

クラス10~50個の中規模プログラミングに当たって,以下の問題がよく出てきて,
「簡潔な方法はないものか・・・」と悩んでいます.

●前提条件
【・「クラスAに持たれているクラスB( A have a B 関係)において,
  クラスBからクラスAのあるメンバ変数(プロパティ)だけを触りたい」】

この場合,私はよく以下のようにしてしまい,クラス間の独立性を無くしてしまいます.
●方法1:
・クラスBのコンストラクタに「自分の持ち主であるクラスAのオブジェクト」を引数に取り,クラスBの変数(プロパティ)usedClassAとする.

=======
C言語風に書くと,
<code>
public void クラスA{
  クラスB usingClassB = new クラスB(); // 持っているクラスB
  int commonNum = 0;
  public void AddCommonNum(){
      commonNum++;
   }
   ...
   (その他の処理)
   ...
}

public void クラスB{
   class usedClassA;    // 持ち主のクラスA

   // コンストラクタ
   public クラスB(クラスA _usedClassA){
       usedClassA = _usedClassA;
   }
   public void AddCommonNum(){
       _usedClassA.AddCommonNum();
   }
}
<\code>
となります.

この方法の問題点は,クラスAとクラスBに<双方向の依存関係を作っている>ことで,
クラスAの設計(ここではAddCommonNum())が変更されたときに,クラスBの内容を変更しなければならない可能性があることから,拡張性に欠けると考えています.

そこで,他に何かいい実装方法が無いか,
教えていただけないでしょうか?
特に,このような前提条件に汎用的に使える方法だと尚良いです.

クラス10~50個の中規模プログラミングに当たって,以下の問題がよく出てきて,
「簡潔な方法はないものか・・・」と悩んでいます.

●前提条件
【・「クラスAに持たれているクラスB( A have a B 関係)において,
  クラスBからクラスAのあるメンバ変数(プロパティ)だけを触りたい」】

この場合,私はよく以下のようにしてしまい,クラス間の独立性を無くしてしまいます.
●方法1:
・クラスBのコンストラクタに「自分の持ち主であるクラスAのオブジェクト」を引数に取り,クラスBの変数(...続きを読む

Aベストアンサー

 こんにちは。
 簡単な話、共通のプロパティクラスを作成して、ClassAとClassBが其れを参照したり更新したりすれば、ClassAとClassBは左程依存しないのでは。
 一応C++で、其れらしき事をしてみましたので、参考程度に。

#pragma warning(disable : 4786)
#include<map>
#include<string>

//プロパティオブジェクトココから
struct IVariantHolder
{
  virtual ~IVariantHolder(){ }
};

template<class __TP>
struct CVariantHolder : public IVariantHolder
{
  typedef typename __TP variant;

  explicit CVariantHolder(const variant& val) : m_val(val){}
  ~CVariantHolder(){}

  variant& Get(){ return m_val; }
  const variant& Get() const { return m_val; }
  operator variant&(){ return m_val; }
  operator const variant&() const { return m_val; }
private:
  variant m_val;
};

struct CPropertyData
{
  typedef std::map<std::string, IVariantHolder*> map_t;
  template<class __TP>
  bool AddProperty(const __TP& tp, const std::string& sPropertyName)
  {
    if(GetProperty(sPropertyName))return false;
    return m_map.insert(std::make_pair(sPropertyName, new CVariantHolder<__TP>(tp))).second;
  }
  IVariantHolder* GetProperty(const std::string& sPropertyName)
  {
    return const_cast<IVariantHolder*>(
                static_cast<const CPropertyData&>(*this).GetProperty(sPropertyName)
                     );
  }
  const IVariantHolder* GetProperty(const std::string& sPropertyName) const
  {
    map_t::const_iterator it = m_map.find(sPropertyName);
    return it == m_map.end() ? 0 : it->second;
  }
private:
  map_t m_map;
};

template<class __TP>
static __TP* Lock(CPropertyData* property, const std::string& sPropertyName)
{
  CVariantHolder<__TP>* pVal = dynamic_cast<CVariantHolder<__TP>*>(property->GetProperty(sPropertyName));
  return pVal ? &pVal->Get() : 0;
}
//プロパティオブジェクトココまで

//テスト用の構造体
struct CommonStruct
{
  CommonStruct(long _l, short _s, char _c) : l(_l), s(_s), c(_c){}
  longl;
  shorts;
  charc;
};

//クラスAとクラスBココから
struct ClassB;
struct ClassA
{
  ClassA(ClassB* p, CPropertyData* property) : m_useClassB(p), m_property(property)
  {
    //ココでメンバ変数(プロパティ)の領域を動的に作成する
    m_property->AddProperty(int(0), "commonNum");
    m_property->AddProperty(CommonStruct(4, 2, 1), "commonStruct");
  }
  void DisplayProperty()
  {
    ::printf("%s %d %s\n", "[commonNum : ", *::Lock<int>(m_property, "commonNum"), "]");

    CommonStruct* p = ::Lock<CommonStruct>(m_property, "commonStruct");
    ::printf("%s <%d><%d><%d> %s\n", "[commonStruct <l><s><c> : ", p->l, p->s, p->c, "]");
  }
private:
  ClassB*m_useClassB;
  CPropertyData*m_property;
};

struct ClassB
{
  explicit ClassB(CPropertyData* property) : m_property(property){}
  void AddCommonNum()
  {
    int* pi = ::Lock<int>(m_property, "commonNum");
    (*pi)++;
  }
  void SetCommonStruct(long l, short s, char c)
  {
    CommonStruct* pc = ::Lock<CommonStruct>(m_property, "commonStruct");
    new (pc) CommonStruct(l, s, c);
  }
private:
  CPropertyData*m_property;
};
//クラスAとクラスBココまで

//お試し
int main()
{
  //両方に共通なプロパティオブジェクト
  CPropertyData property;

  //クラスBに渡す
  ClassB b(&property);

  //クラスAにクラスBとプロパティオブジェクトを渡す
  ClassA a(&b, &property);

  //クラスBでプロパティを操作する
  b.AddCommonNum();
  b.SetCommonStruct(10, 20, 30);

  //クラスAでプロパティを表示する
  a.DisplayProperty();
  return 0;
}

 こんにちは。
 簡単な話、共通のプロパティクラスを作成して、ClassAとClassBが其れを参照したり更新したりすれば、ClassAとClassBは左程依存しないのでは。
 一応C++で、其れらしき事をしてみましたので、参考程度に。

#pragma warning(disable : 4786)
#include<map>
#include<string>

//プロパティオブジェクトココから
struct IVariantHolder
{
  virtual ~IVariantHolder(){ }
};

template<class __TP>
struct CVariantHolder : public IVariantHolder
{
  typedef typename __T...続きを読む

Q食酢の中和滴定 誤差 教えてください

10倍希釈試料中の酸濃度の相対誤差を4.0%(二次標準液の誤差1.9%、ホールピペットの誤差0.2%、ビュレットの誤差1.9%)と求めました。原液中の相対誤差はどのようにして求めればよいかを教えてください。

Aベストアンサー

回答が遅くなりまして失礼いたしました。
補足ありがとうございます。

>|ΔX/X|が相対誤差である。

では、測定値Xと誤差ΔXの値はいくつですか?
実験したのであれば、それぞれの値が分かっているはずですね。

もし、それが分からないのであれば、何か勘違いがあるか、見落としている点があるということです。

測定値というのは実際に測定した値ですから、実験したのであれば、必ず測定値が分かっているはずです。もし、それが分からないようであれば、そもそも実験をちゃんとやっていないということになります。

次に誤差ですが、最初から誤差の値は分かりません。ですから誤差の値を求める実験・測定をしているはずです。もし、そうした測定をしていなければ、例えば、実験の各段階で、誤差をいくつであると仮定しているとか、何か誤差の値を求めるための条件があるはずです。

ですので、まずは、以上のことをきちんと整理して下さい。

QFortran90/Fortran95→Fortran77

大学の授業でFortranを使ったプログラミングを勉強しています。

以下の文が大学のPCに入っているコンパイラでは問題なくコンパイルでき実行できるのですが、家のPCだとコンパイルすることが出来ません(以下の文でエラーが出ます)
大学のPCの開発環境はFujitsu-FORTRANだと思います(^ ^;
家のPCはSalford FTN77 Personal Edition CompilerとCPad for Salford FTN77を組み合わせて使用しています

なぜエラーがでるのか自分なりに考えた結果、Fortran90/Fortran95のプログラムをFortran77のコンパイラでコンパイルしているからだと思います(全くの勘違いだったら指摘して下さい)

Fortran90/Fortran95の開発環境がフリーで整えばいいのですが、見つからないのでプログラムを修正したいと思います そこで、力を貸していただきたいのです

前置きが長くなりましたが、エラーが出る文は以下のところです
open(8,file='freq_ex13.dat',action='write',status='replace')
ここを、Fortran77のコンパイラでコンパイルできるようにアドバイスを下さい よろしくお願いします

大学の授業でFortranを使ったプログラミングを勉強しています。

以下の文が大学のPCに入っているコンパイラでは問題なくコンパイルでき実行できるのですが、家のPCだとコンパイルすることが出来ません(以下の文でエラーが出ます)
大学のPCの開発環境はFujitsu-FORTRANだと思います(^ ^;
家のPCはSalford FTN77 Personal Edition CompilerとCPad for Salford FTN77を組み合わせて使用しています

なぜエラーがでるのか自分なりに考えた結果、Fortran90/Fortran95のプログラムをFortran77のコンパイラでコン...続きを読む

Aベストアンサー

action='write'を削除してみては?
8番にREADを使わなければいいだけの話です。
http://docs.hp.com/ja/B3908-90007/ch10s65.html#id21163286

Fortranはコンパイラ毎に独自の拡張が相当されてますから、移植する際にはどの拡張が使えるのか把握する必要があります。
使えない場合はコンパイルエラーが返ってくるのですぐにわかりますけど。
http://www.cc.nao.ac.jp/vppman/HTML/japan/langFort/fvp11/fvp00079.htm

参考URL:http://docs.hp.com/ja/B3908-90007/ch10s65.html#id21163286

Q測量の誤差全般について

標記の件について、ネットや参考書を読んでいるのですが、
恥ずかしながら今ひとつ理解できません。
すみませんが、御教示頂きたく宜しくお願い致します。

質問1
「確率誤差」とは50%の確率で生じる誤差の範囲とすると、「平均2乗誤差」も何%で生じる誤差の範囲とかで定義されるのでしょうか?(「平均2乗誤差」がイメージできなくて悩んでおります。)
 また、「平均2乗誤差」が「ガウスの誤差曲線」にどう関係するか合わせて御教示お願いします。
 

質問2
「確率誤差」は、下式の様に「標準偏差」や「平均2乗誤差」を使ってを求める様ですが、
それぞれ違った値で導かれた結果をどう理解して使い分けたらようのでしょうか?


ε=0.6745×標準偏差
ε=0.6745×平均2乗誤差

Aベストアンサー

ANo.2です。ANo.3の補足の質問にお答えします。

>誤差曲線は以下のような理解でよろしいでしょうか?

前回の文献の用語に従えば、そのとおりだと思います。

蛇足ですが、「確率誤差」や「平均2乗誤差」の大きさは、矢印の、中心線から左側部分(あるいは右側部分)の長さに一致します。

QFortranの変数の配列の設定値を計算中に設定するには?

FortranでプログラムをつくるときAという変数にBの値の範囲で配列を設定する。A(B)
このとき、プログラム作成時にはAには具体的な数値を設定しておかなくても良いですが、Bには具体的に配列の数を設定しておく必要があるように思います。
 質問は、
 プログラムが動く初めにはBに具体的な値を入れず、プログラム作動状況に応じてプログラム作動中にBの配列の範囲を設定できないものでしょうか?

Aベストアンサー

プログラム A がサブルーチンなら可能です。

メインプログラム
 C=10
 if( C .GT. 0 ) call A(C)
 STOP
 END
 
サブルーチン A
 sub A(B)
  dim(B)
 returne

Qランダム誤差と系統誤差

ランダム誤差→極限的に正規分布に従うようなランダムな誤差
系統誤差→「真の値」にたいして系統的にずれて観測されるランダムでない誤差

として、普通のものさしなどの公差や、読み取り誤差、また、電流計の公差はどちらにあたるでしょうか?

Aベストアンサー

#5お礼欄に関して
>A.「極限的に正規分布に従うようなランダムな誤差」
>B.「多数測定で誤差を低減できる」
>というのが全く同じことのように感じるということです。
多分同じことを別の表現で表しているのだと思います。

で、(1),(2)に関して、(2)は必ずしも成立しないような。(中心極限定理って、母集団の分布が正規分布である必要はなかったかと)

測定誤差に関しては、
a)真値がAの事象があって、
b)これを無限回測定したと仮定すると、測定結果は、平均値A'、分散σ2の集団になる。
c)有限回の測定は、b)を母集団として、そこから有限個抽出する操作に該当。
d)c)の平均値はb)の平均値A'に収束し、分散はσ2/N(中心極限定理)の正規分布に収束する

統計処理はc)からb)を推定する処理で、A'とAの差異(これが系統誤差になるかと)は検出できないように思います。

Qfortranで**の意味は?

フォートランのプログラム中に**というものがでてきました。
例えばN=2**L/Rと使われていました。(変数はすべて整数型です。)

フォートランで**は*と同じと考えてよいのでしょうか?
わかる方がいましたら教えていただけないでしょうか?
よろしくお願いいたします。

Aベストアンサー

べき乗です。
演算の優先度は乗除算より高いので
2**L/R
は、2のL乗をRで割ることになります。

Q平均誤差について

物理学の講義で判らなかったことですが、内容が数学的だったので、こちらで質問させてください。

平均誤差と確率誤差の違いが判りません。
講義で、平均誤差と確率誤差、最小二乗法、誤差の伝播の法則などを同時に教えられたので混乱しているのだと思います。
その時にとったノートは、とにかく黒板を写しただけになってしまい、何がどのことなのか判らなくなっています。
平均誤差・確率誤差を教えていただければ幸いです。
最小二乗法はなんとなく判ったので、誤差の伝播の法則はもう少し頑張ってみようと思います。

判りにくい質問文で申し訳ありませんが、よろしくお願いします。

Aベストアンサー

平均誤差eは、誤差の絶対値の平均値であり、式で示せば
e=Σ(i=1→n)|[各測定値]i-[平均値]|/n
これは概念としては単純なのですが、計算が難しく、物理に限らず一般に統計では、あまり用いられません。

そこで登場するのが確率誤差になります。

確率誤差というのは、その誤差を超えるものが全体の50%、誤差以内が50%という境界を定義する誤差で、標準偏差のの0.674倍です。
標準偏差をσ(シグマ)、標準誤差をεと表記します。
ε = 0.674σ
標準偏差σは分散Vの平方根です。
σ=√V
V=Σ(i=1→n)([各測定値]i-[平均値])^2 /n

標準偏差は非常によく用いられる概念なので、覚えること必須です。
エクセルの基本関数の一つでもあります。
(stdなんちゃら関数です)

学力試験の統計結果で「偏差値」が用いられますが、じつは、それは、平均値を50、標準偏差が10になるように統計処理したものなんです。
ですから、偏差値で言うと、50±6.74の範囲にいる受験者が全体の50%とということになります。
56.74以上の偏差値でしたら、4人に1人の優秀者ということですね。

ちなみに、50±10、すなわち、平均値±標準偏差の範囲には、全体の約68.3%が入ります。
偏差値60以上の人は、全体の15.8%になります。

平均誤差eは、誤差の絶対値の平均値であり、式で示せば
e=Σ(i=1→n)|[各測定値]i-[平均値]|/n
これは概念としては単純なのですが、計算が難しく、物理に限らず一般に統計では、あまり用いられません。

そこで登場するのが確率誤差になります。

確率誤差というのは、その誤差を超えるものが全体の50%、誤差以内が50%という境界を定義する誤差で、標準偏差のの0.674倍です。
標準偏差をσ(シグマ)、標準誤差をεと表記します。
ε = 0.674σ
標準偏差σは分散Vの平方根です。
σ=√V
...続きを読む

Q(fortran) run-time erro M6201: MATH - **:DOMAIN error とは何でしょうか?

あるサブルーチンを呼ぶcall 文を書くと,こういうエラーが実行時に出てしまうのですが,
何が原因なのでしょうか?ちなみにコンパイル時には何もエラーはでません.
わかる方教えていただけないでしょうか?
よろしくお願いします.
ソフトはVisual Fotran 5.0 を使っています.

Aベストアンサー

関数の定義域の問題のような印象を受けますが。
log()に負の数を渡しているとか
asin()に1より大きな数を渡しているとか
していませんか?


人気Q&Aランキング