Jak określić wersję systemu operacyjnego w systemie OS X lub iOS (bez użycia Gestalt)?
Funkcja Gestalt() znajdująca się w CarbonCore/OSUtils.h
została wycofana z systemu OS X 10.8 Mountain Lion.
Często używam tej funkcji do testowania wersji systemu operacyjnego OS X w czasie wykonywania (zobacz przykład poniżej).
Jakie inne API można wykorzystać do sprawdzenia wersji systemu operacyjnego OS X w aplikacji Cocoa?
int main() {
SInt32 versMaj, versMin, versBugFix;
Gestalt(gestaltSystemVersionMajor, &versMaj);
Gestalt(gestaltSystemVersionMinor, &versMin);
Gestalt(gestaltSystemVersionBugFix, &versBugFix);
printf("OS X Version: %d.%d.%d\n", versMaj, versMin, versBugFix);
}
12 answers
Na OS X 10.10 (i iOS 8.0) możesz użyć [[NSProcessInfo processInfo] operatingSystemVersion]
, która zwraca strukturę NSOperatingSystemVersion
zdefiniowaną jako
typedef struct {
NSInteger majorVersion;
NSInteger minorVersion;
NSInteger patchVersion;
} NSOperatingSystemVersion;
Istnieje również metoda w NSProcessInfo, która zrobi porównanie za ciebie:
- (BOOL)isOperatingSystemAtLeastVersion:(NSOperatingSystemVersion)version
Strzeżcie się , chociaż udokumentowane, że są dostępne w OS X 10.10 i późniejszych, zarówno operatingSystemVersion
, jak i isOperatingSystemAtLeastVersion:
istnieją na OS X 10.9 (prawdopodobnie 10.9.2) i działają zgodnie z oczekiwaniami. Oznacza to, że nie wolno sprawdzać, czy NSProcessInfo
odpowiada na te selektory, aby sprawdzić, czy działasz na OS X 10.9 lub 10.10.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-04-10 11:40:48
W wierszu poleceń:
$ sysctl kern.osrelease
kern.osrelease: 12.0.0
$ sysctl kern.osversion
kern.osversion: 12A269
Programowo:
#include <errno.h>
#include <sys/sysctl.h>
char str[256];
size_t size = sizeof(str);
int ret = sysctlbyname("kern.osrelease", str, &size, NULL, 0);
Wersja Darwina do wydania OS X:
17.x.x. macOS 10.13.x High Sierra
16.x.x macOS 10.12.x Sierra
15.x.x OS X 10.11.x El Capitan
14.x.x OS X 10.10.x Yosemite
13.x.x OS X 10.9.x Mavericks
12.x.x OS X 10.8.x Mountain Lion
11.x.x OS X 10.7.x Lion
10.x.x OS X 10.6.x Snow Leopard
9.x.x OS X 10.5.x Leopard
8.x.x OS X 10.4.x Tiger
7.x.x OS X 10.3.x Panther
6.x.x OS X 10.2.x Jaguar
5.x OS X 10.1.x Puma
Próbka do pobrania i przetestowania wersji:
#include <string.h>
#include <stdio.h>
#include <sys/sysctl.h>
/* kernel version as major minor component*/
struct kern {
short int version[3];
};
/* return the kernel version */
void GetKernelVersion(struct kern *k) {
static short int version_[3] = {0};
if (!version_[0]) {
// just in case it fails someday
version_[0] = version_[1] = version_[2] = -1;
char str[256] = {0};
size_t size = sizeof(str);
int ret = sysctlbyname("kern.osrelease", str, &size, NULL, 0);
if (ret == 0) sscanf(str, "%hd.%hd.%hd", &version_[0], &version_[1], &version_[2]);
}
memcpy(k->version, version_, sizeof(version_));
}
/* compare os version with a specific one
0 is equal
negative value if the installed version is less
positive value if the installed version is more
*/
int CompareKernelVersion(short int major, short int minor, short int component) {
struct kern k;
GetKernelVersion(&k);
if ( k.version[0] != major) return major - k.version[0];
if ( k.version[1] != minor) return minor - k.version[1];
if ( k.version[2] != component) return component - k.version[2];
return 0;
}
int main() {
struct kern kern;
GetKernelVersion(&kern);
printf("%hd %hd %hd\n", kern.version[0], kern.version[1], kern.version[2]);
printf("up: %d %d eq %d %d low %d %d\n",
CompareKernelVersion(17, 0, 0), CompareKernelVersion(16, 3, 0),
CompareKernelVersion(17, 3, 0), CompareKernelVersion(17,3,0),
CompareKernelVersion(17,5,0), CompareKernelVersion(18,3,0));
}
Wynik na moim komputerze macOs High Sierra 10.13.2
17 3 0
up: -3 -1 eq 0 0 low 2 1
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-02-18 14:02:08
Istnieje wartość NSAppKitVersionNumber, której możesz użyć do sprawdzenia różnych wersji AppKit, chociaż nie odpowiadają one dokładnie wersjom systemu operacyjnego
if (NSAppKitVersionNumber <= NSAppKitVersionNumber10_7_2) {
NSLog (@"We are not running on Mountain Lion");
}
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-07-28 00:45:49
Istnieje API cocoa. Możesz uzyskać ciąg wersji os X z klasy NSProcessInfo.
Kod, aby uzyskać ciąg wersji systemu operacyjnego znajduje się poniżej..
NSString * operatingSystemVersionString = [[NSProcessInfo processInfo] operatingSystemVersionString];
NSLog(@"operatingSystemVersionString => %@" , operatingSystemVersionString);
// ===>> Wersja 10.8.2 (Build 12c2034) wartość wyniku
To nie jest przestarzałe.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-06-05 09:13:54
Istnieje również kCFCoreFoundationVersionNumber, który może być użyty, jeśli potrzebujesz tylko sprawdzić minimalną wersję do obsługi. Ma to tę zaletę, że działa wstecz do wersji 10.1 i można to zrobić w C, C++ i Objective-C. {]}
Na przykład, aby sprawdzić dla 10.10 lub większej:
#include <CoreFoundation/CoreFoundation.h>
if (floor(kCFCoreFoundationVersionNumber) > kCFCoreFoundationVersionNumber10_9) {
printf("On 10.10 or greater.");
}
Będziesz musiał połączyć się ze strukturą Fundacji (CoreFoundation).
Działa również w języku Swift w dokładnie taki sam sposób. Oto kolejny przykład:
import Foundation
if floor(kCFCoreFoundationVersionNumber) > kCFCoreFoundationVersionNumber10_8 {
println("On 10.9 or greater.")
} else if floor(kCFCoreFoundationVersionNumber) > kCFCoreFoundationVersionNumber10_9 {
println("On 10.10 or greater.")
}
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-04-13 21:57:08
Lub, mówiąc prościej, oto kod:
NSDictionary *version = [NSDictionary dictionaryWithContentsOfFile:@"/System/Library/CoreServices/SystemVersion.plist"];
NSString *productVersion = [version objectForKey:@"ProductVersion"];
NSLog (@"productVersion =========== %@", productVersion);
Mam nadzieję, że to komuś pomoże.Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-02-22 15:13:12
Możesz łatwo uzyskać główną, podrzędną wersję systemu operacyjnego za pomocą NSOperatingSystemVersion
NSOperatingSystemVersion version = [[NSProcessInfo processInfo] operatingSystemVersion];
NSString* major = [NSString stringWithFormat:@"%d", version.majorVersion];
NSString* minor = [NSString stringWithFormat:@"%d", version.minorVersion];
NSString* patch = [NSString stringWithFormat:@"%d", version.patchVersion];
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-08-13 07:54:27
Tego używam:
NSInteger osxVersion;
if (floor(NSAppKitVersionNumber) <= NSAppKitVersionNumber10_6) {
//10.6.x or earlier systems
osxVersion = 106;
NSLog(@"Mac OSX Snow Leopard");
} else if (floor(NSAppKitVersionNumber) <= NSAppKitVersionNumber10_7) {
/* On a 10.7 - 10.7.x system */
osxVersion = 107;
NSLog(@"Mac OSX Lion");
} else if (floor(NSAppKitVersionNumber) <= NSAppKitVersionNumber10_8) {
/* On a 10.8 - 10.8.x system */
osxVersion = 108;
NSLog(@"Mac OSX Moutain Lion");
} else {
/* 10.9 or later system */
osxVersion = 109;
NSLog(@"Mac OSX: Mavericks or Later");
}
To jest zalecane w AppKit Release Notes
Reading/System/Library/CoreServices / SystemVersion.plist nie jest możliwe, jeśli aplikacja jest piaskownica
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2014-06-29 08:38:12
Jeśli masz aplikację, która musi działać w wersji 10.10, jak również w poprzednich wersjach, oto rozwiązanie:
typedef struct {
NSInteger majorVersion;
NSInteger minorVersion;
NSInteger patchVersion;
} MyOperatingSystemVersion;
if ([[NSProcessInfo processInfo] respondsToSelector:@selector(operatingSystemVersion)]) {
MyOperatingSystemVersion version = ((MyOperatingSystemVersion(*)(id, SEL))objc_msgSend_stret)([NSProcessInfo processInfo], @selector(operatingSystemVersion));
// do whatever you want with the version struct here
}
else {
UInt32 systemVersion = 0;
OSStatus err = Gestalt(gestaltSystemVersion, (SInt32 *) &systemVersion);
// do whatever you want with the systemVersion as before
}
Zauważ, że nawet 10.9 wydaje się odpowiadać selektorowi operat systemversion, więc myślę, że to było tylko prywatne API w 10.9 (ale nadal działa).
Działa to na wszystkich wersjach OS X i nie polega na parsowaniu łańcuchów znaków lub We/Wy pliku.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2014-08-12 13:32:45
Jest uname(3)
:
The
uname()
funkcja przechowuje zakończone nul ciągi informacji identyfikujących bieżący system w strukturze, do której odwołuje sięname
.The
utsname
struktura jest zdefiniowana w<sys/utsname.h>
plik nagłówkowy oraz zawiera następujących członków:
sysname
- Nazwa implementacji systemu operacyjnego.nodename
- Nazwa sieciowa tego urządzenia.release
- poziom Release systemu operacyjnego.version
- poziom wersji systemu operacyjnego.machine
- Platforma sprzętowa Maszyny.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-06-18 00:29:02
Jest to tak naprawdę kompilacja powyższych odpowiedzi, z pewnymi dalszymi wskazówkami dla deweloperów w potrzebie.
OS-X udostępnia swoją wersję w trybie runtime na kilka sposobów. Każdy sposób lepiej pasuje do konkretnego scenariusza rozwoju. Postaram się podsumować je wszystkie i mam nadzieję, że inni uzupełnią moją odpowiedź, jeśli o czymś zapomniałem.
Po pierwsze, obszerna lista sposobów uzyskania wersji systemu operacyjnego.
- narzędzie i funkcja wiersza poleceń
uname
dostarcza Uniksa (darwin) wersja systemu operacyjnego. Chociaż nie jest to wersja marketingowa systemu operacyjnego, jest z nim dopasowana wyjątkowo, więc można wywnioskować z niego wersję marketingową OS-X. -
sysctl kern.osrelease
wiersz poleceń (lub Funkcjasysctlbyname("kern.osrelease", str, &size, NULL, 0)
) dostarczy te same informacje co uname, nieznacznie łatwiejsze do przetworzenia. -
Gestalt(gestaltSystemVersionMajor)
(z wariantami "Minor
"iBugFix
" jest najstarszy (pre-Carbon!) API, aby uzyskać wersję marketingową systemu operacyjnego, nadal obsługiwaną przez długo przestarzałą. Dostępne w C z frameworka CoreServices, ale nie polecam. -
NSAppKitVersionNumber
jest stałą zmiennoprzecinkową frameworka AppKit, która zapewni wersję OS-X Appkit (dostosowaną do wersji OS), dostępną dla wszystkich aplikacji, które łączą się z AppKit. Zawiera również obszerne wyliczenie wszystkich możliwych wersji (np.NSAppKitVersionNumber10_7_2
) -
kCFCoreFoundationVersionNumber
jest stałą floatową frameworka CoreFoundation, identyczną z odpowiednikiem Appkit, dostępną dla wszystkich aplikacji połączonych z CoreFoundation, zarówno w C, Obj-C, jak i Swift. To również zapewnia wszystkie wersje systemu OS X (np.kCFCoreFoundationVersionNumber10_9
) -
[[NSProcessInfo processInfo] operatingSystemVersionString];
to API Cocoa dostępne w Obj - C zarówno dla aplikacji OS-X, jak i iOS. - istnieje zasób .plist w
/System/Library/CoreServices/SystemVersion.plist
, który między innymi zawiera wersję systemu operacyjnego w kluczu "ProductVersion". NSProcessInfo odczytuje swoje informacje z tego pliku, ale możesz to zrobić bezpośrednio za pomocą wybranego API do odczytu PList.
Aby uzyskać więcej informacji na temat każdej opcji-zapoznaj się z odpowiedziami powyżej. Jest tam mnóstwo informacji!
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-04-18 09:55:19
Spóźniłem się na mecz, ale wylądowałem tutaj, szukając odpowiedzi. Jeśli to coś warte, może przyda się komuś innemu;
W przeszłości używałem podejścia wiersza poleceń:
sw_vers
Co daje:
ProductName: Mac OS X
ProductVersion: 10.13.6
BuildVersion: 17G65
Każdy wiersz może być zapytany indywidualnie (pamiętaj o notacji camelback):
sw_vers -productVersion
10.13.6
sw_vers -productName
Mac OS X
sw_vers -buildVersion
17G65
Powiedziawszy to, dziękuję za wszystkie inne rozwiązania wymienione tutaj ...
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-08-14 17:27:00