सी, 174 167 152 बाइट्स
रिकर्सिव फ़ंक्शन f
, जो मेमोरी को लीक करता है ( 152 ):
#include"object.h"
size_t f(array_t*a){size_t t=0,i=0;for(;i<array_length(a);i++){object_t*o=array_get_copy(a,i,0);t+=o->type==6?f(o->ary):1;}return t;}
पुनरावर्ती, f
जो 167 पर, संदर्भ का उपयोग करते हुए लीक नहीं करता है :
#include"object.h"
size_t f(array_t*a){size_t t=0,i=0;for(;i<array_length(a);i++){object_t**o=array_get_ref(a,i,0);t+=*o->type==t_array?f(*o->ary):1;}return t;}
Ungolfed:
size_t get_recursize (const array_t* const a) {
pfn();
object_failnull(a);
size_t out = 0;
for (size_t i = 0; i < array_length(a); i++) {
object_t** o = array_get_ref(a, i, NULL);
if ( (*o)->type == t_array ) {
out += get_recursize((*o)->ary);
} else {
++out;
}
}
return out;
}
"लेकिन कैसे," आप पूछते हैं, "इसका उत्तर सी में हो सकता है? निश्चित रूप से, सी में कोई प्रबंधित सरणियां नहीं हैं, और आप वास्तव में विषम सरणियां नहीं कर सकते हैं ...?"
"अहा," मैं उत्तर देता हूं, "क्योंकि मैं (GNU-ish) C11 और ISO C ++ 11" के लिए "ऑब्जेक्ट" की एक सरल प्रणाली पर काम कर रहा हूं।
इस समारोह के लिए पूरा डेमो कार्यक्रम है:
#include "../calc/object/object.h"
size_t get_recursize (const array_t* const a);
define_array_new_fromctype(ssize_t);
int main (void) {
size_t len = 6;
static const ssize_t h[6] = { -1, 3, -5, 7, -9, 11 };
array_t* a = array_new_from_ssize_t_lit(h, len, t_realint);
size_t rsize = get_recursize(a);
printf("Recursive size of a: %zu\n", rsize);
object_t* asobj = object_new(t_array, a);
array_destruct(a);
array_t* b = array_new(NULL, -1);
for (size_t j = 0; j < 10; j++) {
array_append(b, asobj);
}
object_destruct(asobj);
rsize = get_recursize(b);
printf("Recursive size of b: %zu\n", rsize);
asobj = object_new(t_array, b);
array_destruct(b);
array_t* c = array_new(NULL, -1);
for (size_t i = 0; i < 100; i++) {
array_append(c, asobj);
}
object_destruct(asobj);
rsize = get_recursize(c);
printf("Recursive size of c: %zu\n", rsize);
array_destruct(c);
return EXIT_SUCCESS;
}
size_t get_recursize (const array_t* const a) {
pfn();
object_failnull(a);
size_t out = 0;
for (size_t i = 0; i < array_length(a); i++) {
object_t** o = array_get_ref(a, i, NULL);
if ( (*o)->type == t_array ) {
out += get_recursize((*o)->ary);
} else {
++out;
}
}
return out;
}
अभी, यह यहाँ रहता है और आपको इसके उपयोग के लिए रेपो की आवश्यकता होगी।
आपको libfnv
अपने प्लेटफ़ॉर्म के लिए संकलित फाउलर-नॉल-वो हैश लाइब्रेरी की भी आवश्यकता होगी । यह उस रिपॉजिटरी में है और आप इसे यहां ले भी सकते हैं ।
तब आप कर सकते हैं cc -DNODEBUG size.c path/to/libfnv.a -o size
।
कार्यान्वयन जरूरी नहीं है:
$ valgrind --leak-check=full --track-origins=yes --show-leak-kinds=all ./size
==24127== Memcheck, a memory error detector
==24127== Copyright (C) 2002-2015, and GNU GPL'd, by Julian Seward et al.
==24127== Using Valgrind-3.12.0.SVN and LibVEX; rerun with -h for copyright info
==24127== Command: ./size
==24127==
Recursive size of a: 6
Recursive size of b: 60
Recursive size of c: 6000
==24127==
==24127== HEAP SUMMARY:
==24127== in use at exit: 0 bytes in 0 blocks
==24127== total heap usage: 22,900 allocs, 22,900 frees, 615,584 bytes allocated
==24127==
==24127== All heap blocks were freed -- no leaks are possible
==24127==
==24127== For counts of detected and suppressed errors, rerun with: -v
==24127== ERROR SUMMARY: 0 errors from 0 contexts (suppressed: 0 from 0)
लेकिन यह काम करता है! मास्टर के लिए अंतिम प्रतिबद्ध (जो इस कार्यक्रम को संकलित किया गया था) 2 दिन पहले था, जिसका अर्थ है कि यह जमा मान्य है।