配列が持つ値の数を見つける方法はありますか?配列の最後に到達したかどうかを検出することもできます。
配列が持つ値の数を見つける方法はありますか?配列の最後に到達したかどうかを検出することもできます。
回答:
Cスタイルの配列を意味する場合は、次のようなことができます。
int a[7];
std::cout << "Length of array = " << (sizeof(a)/sizeof(*a)) << std::endl;
これはポインタでは機能しません(つまり、次のいずれでも機能しません)。
int *p = new int[7];
std::cout << "Length of array = " << (sizeof(p)/sizeof(*p)) << std::endl;
または:
void func(int *p)
{
std::cout << "Length of array = " << (sizeof(p)/sizeof(*p)) << std::endl;
}
int a[7];
func(a);
C ++では、この種の動作が必要な場合は、コンテナークラスを使用する必要があります。たぶんstd::vector
。
他の人が言ったように、あなたは使うことができますがsizeof(arr)/sizeof(*arr)
、これは配列ではないポインタ型に対してあなたに間違った答えを与えるでしょう。
template<class T, size_t N>
constexpr size_t size(T (&)[N]) { return N; }
これには、配列以外の型のコンパイルに失敗するという優れた特性があります(Visual Studioには、_countof
これを行う機能があります)。constexpr
それはマクロ(私が知っている、少なくともなし)以上のいずれかの欠点を持っていないので、このコンパイル時式ます。
またstd::array
、ネイティブC配列にオーバーヘッドをかけずにその長さを公開するC ++ 11からの使用を検討することもできます。
C ++ 17を有しているstd::size()
で<iterator>
同じことを行い、あまりにもSTLコンテナ(おかげで動作し、ヘッダ@ジョンC)。
T(arg&)[N]
。
extent
、これを見ると、上記の関数(このユースケースの場合)ほど便利ではない2つの特性があります。(1)(コンパイルエラーではなく)ポインターに対してゼロを返します。(2)型パラメーターが必要なため、変数をチェックするために実行する必要があるdecltype
実行すると、sizeof( myArray )
あなたはその配列に割り当てられた合計バイト数を取得します。次に、配列内の1つの要素のサイズで除算することにより、配列内の要素の数を確認できます。sizeof( myArray[0] )
これは古い質問ですが、C ++ 17への回答を更新する価値はあります。標準ライブラリにはstd::size()
、stdコンテナまたはCスタイルの配列の両方の要素数を返すテンプレート関数があります。例えば:
#include <iterator>
uint32_t data[] = {10, 20, 30, 40};
auto dataSize = std::size(data);
// dataSize == 4
配列が持つ値の数を見つける方法はありますか?
はい!
試す sizeof(array)/sizeof(array[0])
配列の最後に到達したかどうかを検出することもできます。
あなたの配列が文字の配列(すなわち文字列)でない限り、私はこれのための方法を見ません。
PS:C ++では常にを使用してくださいstd::vector
。いくつかの組み込み関数と拡張機能があります。
std::vector
size()
ベクトルの要素数を返すメソッドがあります。
(はい、これはほほえみの答えです)
#include <iostream>
int main ()
{
using namespace std;
int arr[] = {2, 7, 1, 111};
auto array_length = end(arr) - begin(arr);
cout << "Length of array: " << array_length << endl;
}
C ++ 11以降、いくつかの新しいテンプレートが導入され、配列の長さを扱う際の負担を軽減するのに役立ちます。それらはすべてheaderで定義されてい<type_traits>
ます。
T
が配列型の場合、配列の次元数に等しいメンバー定数値を提供します。その他のタイプの場合、値は0です。
場合T
、アレイタイプである、に沿った要素の数に等しいメンバー定数値を提供しN
た場合、アレイの第次元をN
[0、ですstd::rank<T>::value
)。その他のタイプの場合、またはT
最初の次元に沿った未知の境界の配列でN
0の場合、値は0です。
T
がなんらかの型の配列である場合X
、メンバーのtypedef型と等しいを提供します。X
それ以外の場合、型はT
です。T
が多次元配列の場合、最初の次元のみが削除されることに注意してください。
std::remove_all_extents<T>::type
T
が何らかのタイプの多次元配列である場合X
、メンバーのtypedefタイプをに等しく提供します。X
それ以外の場合、タイプはT
です。
多次元配列の任意の次元の長さを取得するには、をdecltype
使用してと組み合わせることができますstd::extent
。例えば:
#include <iostream>
#include <type_traits> // std::remove_extent std::remove_all_extents std::rank std::extent
template<class T, size_t N>
constexpr size_t length(T(&)[N]) { return N; }
template<class T, size_t N>
constexpr size_t length2(T(&arr)[N]) { return sizeof(arr) / sizeof(*arr); }
int main()
{
int a[5][4][3]{{{1,2,3}, {4,5,6}}, { }, {{7,8,9}}};
// New way
constexpr auto l1 = std::extent<decltype(a)>::value; // 5
constexpr auto l2 = std::extent<decltype(a), 1>::value; // 4
constexpr auto l3 = std::extent<decltype(a), 2>::value; // 3
constexpr auto l4 = std::extent<decltype(a), 3>::value; // 0
// Mixed way
constexpr auto la = length(a);
//constexpr auto lpa = length(*a); // compile error
//auto lpa = length(*a); // get at runtime
std::remove_extent<decltype(a)>::type pa; // get at compile time
//std::remove_reference<decltype(*a)>::type pa; // same as above
constexpr auto lpa = length(pa);
std::cout << la << ' ' << lpa << '\n';
// Old way
constexpr auto la2 = sizeof(a) / sizeof(*a);
constexpr auto lpa2 = sizeof(*a) / sizeof(**a);
std::cout << la2 << ' ' << lpa2 << '\n';
return 0;
}
BTY、多次元配列の要素の総数を取得するには:
constexpr auto l = sizeof(a) / sizeof(std::remove_all_extents<decltype(a)>::type);
または、関数テンプレートに入れます。
#include <iostream>
#include <type_traits>
template<class T>
constexpr size_t len(T &a)
{
return sizeof(a) / sizeof(typename std::remove_all_extents<T>::type);
}
int main()
{
int a[5][4][3]{{{1,2,3}, {4,5,6}}, { }, {{7,8,9}}};
constexpr auto ttt = len(a);
int i;
std::cout << ttt << ' ' << len(i) << '\n';
return 0;
}
それらを使用する方法のより多くの例はリンクをたどることによって見つけることができます。
TR1 / C ++ 11 / C ++ 17の方法もあります(参照してくださいLive on Coliru):
const std::string s[3] = { "1"s, "2"s, "3"s };
constexpr auto n = std::extent< decltype(s) >::value; // From <type_traits>
constexpr auto n2 = std::extent_v< decltype(s) >; // C++17 shorthand
const auto a = std::array{ "1"s, "2"s, "3"s }; // C++17 class template arg deduction -- http://en.cppreference.com/w/cpp/language/class_template_argument_deduction
constexpr auto size = std::tuple_size_v< decltype(a) >;
std::cout << n << " " << n2 << " " << size << "\n"; // Prints 3 3 3
C ++では、std :: arrayクラスを使用して配列を宣言すると、配列のサイズと最後の要素を簡単に見つけることができます。
#include<iostream>
#include<array>
int main()
{
std::array<int,3> arr;
//To find the size of the array
std::cout<<arr.size()<<std::endl;
//Accessing the last element
auto it=arr.end();
std::cout<<arr.back()<<"\t"<<arr[arr.size()-1]<<"\t"<<*(--it);
return 0;
}
実際、配列クラスには、配列を標準のコンテナとして使用できる他の多くの関数があります。
C ++ std :: arrayクラスのリファレンス1 std :: arrayクラスの
リファレンス2リファレンス
内の例が参考になります。
これはかなり古く、伝説的な質問であり、すでに驚くべき答えがたくさんあります。しかし、時間の経過とともに言語に新しい機能が追加されているため、利用可能な新しい機能に従って更新を続ける必要があります。
C ++ 20についてまだ誰も言及していないことに気づきました。だから答えを書くと思った。
C ++ 20では、配列の長さを見つけるための標準ライブラリに追加された新しいより良い方法がありstd:ssize()
ます。この関数はを返しますsigned value
。
#include <iostream>
int main() {
int arr[] = {1, 2, 3};
std::cout << std::ssize(arr);
return 0;
}
C ++ 17には、(当時)でstd::size()
定義されているのと同じ方法のより良い方法がありましたiterator
。
#include <iostream>
#include <iterator> // required for std::size
int main(){
int arr[] = {1, 2, 3};
std::cout << "Size is " << std::size(arr);
return 0;
}
PSこの方法vector
は同様に機能します。
この従来のアプローチは、他の多くの回答ですでに言及されています。
#include <iostream>
int main() {
int array[] = { 1, 2, 3 };
std::cout << sizeof(array) / sizeof(array[0]);
return 0;
}
ちょうどFYI、あなたはこのアプローチは、なぜだろう場合は、配列を別の関数に渡されたときに動作しません。その理由は、
配列はC ++では値で渡されず、代わりに配列へのポインターが渡されます。場合によっては、配列全体を渡すのは負荷の高い操作になることがあります。これをテストするには、配列を関数に渡し、そこで配列に変更を加えてから、配列をメインでもう一度印刷します。更新された結果が表示されます。
そして、ご存じのとおり、このsizeof()
関数はバイト数を提供するため、他の関数では、配列全体ではなく、ポインターに割り当てられたバイト数を返します。したがって、このアプローチは機能しません。
しかし、私はあなたがあなたの要件に従ってこれを行うための良い方法を見つけることができると確信しています。
ハッピーコーディング。
C配列のサイズを取得するために使用できる多くのオプションがあります。
int myArray [] = {0、1、2、3、4、5、7};
1) sizeof(<array>) / sizeof(<type>):
std::cout << "Size:" << sizeof(myArray) / sizeof(int) << std::endl;
2) sizeof(<array>) / sizeof(*<array>):
std::cout << "Size:" << sizeof(myArray) / sizeof(*myArray) << std::endl;
3) sizeof(<array>) / sizeof(<array>[<element>]):
std::cout << "Size:" << sizeof(myArray) / sizeof(myArray[0]) << std::endl;
これがGoogle ProtobufArraySize
からの実装の1つです。
#define GOOGLE_ARRAYSIZE(a) \
((sizeof(a) / sizeof(*(a))) / static_cast<size_t>(!(sizeof(a) % sizeof(*(a)))))
// test codes...
char* ptr[] = { "you", "are", "here" };
int testarr[] = {1, 2, 3, 4};
cout << GOOGLE_ARRAYSIZE(testarr) << endl;
cout << GOOGLE_ARRAYSIZE(ptr) << endl;
ARRAYSIZE(arr)は、sizeof(arr)(配列内のバイト数)およびsizeof(*(arr))(1つの配列要素内のバイト数)を検査することによって機能します。前者が後者で割り切れる場合、おそらくarrは配列です。その場合、除算結果は配列内の要素の数になります。そうでない場合、arrを配列にすることはできません。コードがコンパイルされないように、コンパイラエラーが生成されます。
boolのサイズは実装によって定義されるため、最終結果の型がsize_tになるように、!(sizeof(a)&sizeof(*(a)))をsize_tにキャストする必要があります。
このマクロは、特定のポインター、つまりポインターのサイズが指示先のサイズで割り切れるポインターを誤って受け入れるため、完全ではありません。すべてのコードはポインターが4バイトである32ビットコンパイラーを経由する必要があるため、これは、サイズが3または4より大きい型へのすべてのポインターが(正当に)拒否されることを意味します。
int nombres[5] = { 9, 3 };
この関数はの5
代わりに戻ります2
。
C ++ / CXの場合(Visual StudioでC ++を使用してUWPアプリを作成する場合など)、size()
関数を使用するだけで、配列内の値の数を見つけることができます。
ソースコード:
string myArray[] = { "Example1", "Example2", "Example3", "Example4" };
int size_of_array=size(myArray);
あなたcout
がsize_of_array
出力した場合:
>>> 4
sizeof(array_name)
配列全体のサイズをsizeof(int)
示し、すべての配列要素のデータ型のサイズを示します。
したがって、配列全体のサイズを配列の1つの要素のサイズで割ると、配列の長さがわかります。
int array_name[] = {1, 2, 3, 4, 5, 6};
int length = sizeof(array_name)/sizeof(int);
回答:
int number_of_elements = sizeof(array)/sizeof(array[0])
説明:
コンパイラーは、データのタイプごとに特定のサイズのメモリー・チャンクを別に設定し、配列はそれらのグループにすぎないため、配列のサイズをデータ・タイプのサイズで除算するだけです。30個の文字列の配列がある場合、システムは配列の各要素(文字列)に24バイトを確保します。30要素で、これは合計720バイトです。720/24 == 30要素。そのための小さくてタイトなアルゴリズムは次のとおりです。
int number_of_elements = sizeof(array)/sizeof(array[0])
これは
number_of_elements = 720/24
カスタムデータ型であっても、配列がどのデータ型であるかを知る必要がないことに注意してください。
考えただけですが、カウンター変数を作成し、配列サイズを[0]の位置に格納することにしました。関数に含まれていたコードのほとんどを削除しましたが、ループを終了すると、prime [0]に「a」の最終値が割り当てられます。私はベクターを使用してみましたが、VS Express 2013はあまり好きではありませんでした。また、 'a'は[0]の上書きを避けるために1から始まり、エラーを避けるために最初に初期化されることに注意してください。私は専門家ではないので、共有したいと思いました。
int prime[] = {0};
int primes(int x, int y){
using namespace std; int a = 1;
for (int i = x; i <= y; i++){prime[a] = i; a++; }
prime[0] = a; return 0;
}
ジェネリックを使用する優れたソリューション:
template <typename T,unsigned S>
inline unsigned arraysize(const T (&v)[S]) { return S; }
次に、呼び出しarraysize(_Array);
て配列の長さを取得します。
constexpr
が修正されます。inline
ではありません。constexpr
かなりモダンですが。テストプログラムが、変数によって長さが指定されるローカル配列を宣言できる別の最新の機能を使用していないことを確認していますか?2つのグローバル配列で試してください。
私はここでトリッキーなソリューションを提供します:
いつでもlength
最初の要素に保存できます:
// malloc/new
arr[0] = length;
arr++;
// do anything.
int len = *(arr-1);
free(--arr);
--arr
呼び出し時に呼び出す必要があるコストですfree
arr
互換性のある型でint
あり、配列が型の最大値より長くない場合にのみ機能します。たとえば、Pascal文字列は実際にはこのトリックを使用したバイト配列です。Pascalでの文字列の最大長は255文字です。
次の方法で配列の長さを確認できます。
int arr[] = {1, 2, 3, 4, 5, 6};
int size = *(&arr + 1) - arr;
cout << "Number of elements in arr[] is "<< size;
return 0;
単にあなたはこのスニペットを使うことができます:
#include <iostream>
#include <string>
#include <array>
using namespace std;
int main()
{
array<int,3> values;
cout << "No. elements in valuea array: " << values.size() << " elements." << endl;
cout << "sizeof(myints): " << sizeof(values) << endl;
}
そしてここに参照があります:http : //www.cplusplus.com/reference/array/array/size/
私は個人的に(何らかの理由で特殊な関数を使用できない場合)最初に配列タイプの互換性を通常の使用方法を超えて拡張することをお勧めします(値≥0を格納していた場合:
unsigned int x[] -> int x[]
配列1の要素を必要以上に大きくするよりも。最後の要素については、拡張型指定子に含まれているが通常は使用しない型を配置します。たとえば、前の例を使用すると、最後の要素は-1になります。これにより、(forループを使用して)配列の最後の要素を見つけることができます。
これを探す最も一般的な理由の1つは、配列を関数に渡し、そのサイズのために別の引数を渡す必要がないためです。また、一般的に配列サイズを動的にすることもできます。その配列にはプリミティブではなくオブジェクトが含まれている可能性があり、オブジェクトは複雑であるため、size_of()はカウントを計算するための安全なオプションではありません。
他の人が示唆しているように、プリミティブ配列の代わりにstd :: vectorまたはリストなどを使用することを検討してください。ただし、古いコンパイラーでは、コンテナーを生成するために醜いpush_back()行の束が必要になるため、単純にそれを実行してもおそらく最終的な解決策が得られません。あなたが私のようであれば、匿名オブジェクトが関与する単一行のソリューションが必要です。
プリミティブ配列の代わりにSTLコンテナーを使用する場合、このSOポストは、それを初期化する方法として 役立ちます。ハードコードされた要素でstd :: vectorを初期化する最も簡単な方法は何ですか?
これは私がこれのために使用している方法であり、コンパイラとプラットフォーム全体で普遍的に機能します:
オブジェクトのコレクションのコンテナーとして構造体またはクラスを作成します。<<の演算子オーバーロード関数を定義します。
class MyObject;
struct MyObjectList
{
std::list<MyObject> objects;
MyObjectList& operator<<( const MyObject o )
{
objects.push_back( o );
return *this;
}
};
構造体をパラメーターとして使用する関数を作成できます。例:
someFunc( MyObjectList &objects );
次に、この関数を次のように呼び出すことができます。
someFunc( MyObjectList() << MyObject(1) << MyObject(2) << MyObject(3) );
このようにして、動的にサイズ設定されたオブジェクトのコレクションを作成し、1つのクリーンな行で関数に渡すことができます。
ページの上部で宣言されたグローバル配列があるとしましょう
int global[] = { 1, 2, 3, 4 };
配列内に(c ++で)要素の数を調べるには、次のコードを入力します。
sizeof(global) / 4;
sizeof(NAME_OF_ARRAY)/ 4は、指定された配列名の要素数を返します。